against list flattening

"Richard A. O'Keefe" <[email protected]>
Newsgroups gmane.comp.ai.prolog.swi
Message-ID <[email protected]>
As I have mentioned, probably often enough to be annoying,
I've been developing a somewhat unusual Smalltalk system,
compiling Smalltalk to C.  Currently I'm comparing its
class library's with Ruby's to see if I'm missing anything
useful.

So far I've found a handful of operations that looked worth
stealXXXXXcopying, although they generally needed refactoring
and in one case I'm so worried about the risks it introduces
that I'll probably pull it out again.

And then I came across

	a.flatten()
	a.flatten(depth)
	a.flatten!()
	a.flatten!()

where a is an Array.  And that just blew up in my face.
My system has no fewer than 62 concrete "indexed sequence"
classes, excluding example files, which introduce several
of their own.  And that's not counting Deques and sorted
sets...  Just what set of classes should be covered by
.flatten()?  How should user-defined classes be plugged in?
What possible sense does it make for .flatten() to flatten
an array of arrays to an array but not an array of strings
to a string?  (In Smalltalk, _none_.)  And what should a
user do who wanted *some* arrays to be flattened but other
arrays to be treated as atomic data?

I just couldn't assign any coherent *meaning* to the flatten
operation.  Oh, I could *implement* it, but I couldn't make
it mean anything *except* the implementation level; I could
not say "this is what it does to a coherent data structure".

Now it is just the same in Prolog.  Pairs and nils are *one*
way to represent a sequence in Prolog, but there are plenty
of others (like unrolled lists, like lazy concatenation,
like applicative random-access stacks -- library(ranstk), ..).
If you are in the habit of using flatten, then which of
the many possible implementations of the sequence idea you
use is no longer just an implementation detail; if your
data structure is included in someone else's list, the choice
affects _their_ result.
And worse, there are some lists you want treated as atomic
and others you do not.  

This is not an argument against flattening (clearly
labelled) *trees*.  That's a useful and unproblematic
operation. It is an argument against flattening "lists".

The clincher, of course, is

	L = [a,B,c], flatten(L, R), B = [2,3]
=>	R = [a.[2,3],c]

which is not flat.
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.