On Mon, 2006-07-10 at 18:16 -0700, Erick Tryzelaar wrote:
> skaller wrote:
> >> language:
> >> 1.2: olabl-like labels/keywords
> >>
> >
> > We have named fields, the syntax is just messy:
> >
> > f struct { x = 1; y = 2; }
> >
> > works now, provided f is written to accept a suitable record type.
> >
> >
> Err, I meant adding sugar for label support :)
Sure, the question is simply how to sugar it.
> >> 1.3: multimethods
> >>
> >
> > Not sure these make sense.
> >
>
> I'm a big fan of the lisp multimethods for their object system,
but Lisp is dynamically typed, Felix isn't. This makes a big
difference: OO systems with dynamic typing are quite different
from those with static typing.
Statically typed OO is broken, and multi-methods do nothing
to fix the problem: on the contrary they just confuse people
into believing it is possible to fix the problem, when in
fact the problem is fundamental -- OO doesn't and cannot
work, end of story -- except in limited circumstances.
Indeed those limits both enlighten us when OO is useful
and simultaneously condemn the idea it is a general development
paradigm as a fraud.
Dynamically typed systems are different because they're *expected*
to fail at run time: there's no concept of type safety in the
first place. So method lookup is just an arbitrary algorithm,
and a multiple dispatch algorithm can be useful.
> fun collide(x:Shape, y:Shape) = // generic bounding box collision
> fun collide(x:Box, y:Box) = // optimized box collision
> fun collide(x:Sphere, y:Shape) = // optimized sphere-bounding box collision
> fun collide(x:Sphere, y:Sphere) = // optimized sphere collision
> fun collide(x:Sphere, y:Box) = // optimized sphere-box collision
This is nothing more than an open form of a match:
match A_shape, B_shape with
| Box of b, Sphere of s => ..
...
except the matching construction is closed, and therefore
able to robustly check all the known cases (though in Felix
the exhaustion check isn't being done :)
This is precisely the kind of problem which CANNOT be solved
with OO, and multiple dispatch does nothing to help. It just
confuses you into believing there is a solution when there
isn't.
Cecil allows the above kind of thing. Can you see the problem?
Hint: the multi-methods break encapsulation.
In the pattern matching solution we ADMIT that it cannot
be done with abstraction: we have to work directly with
representations. But OO LIES and pretends you can have
a base abstraction .. and so you can write algorithms
using those abstractions .. only to find there's no way
to implement the required methods.
In the example, it is clearly a bogus solution.
Using type information is like this is wrong:
it defeats the fundamental concept of modularity:
the Open/Closed principle.
What happens if I invent a new kind of Box, say Box2?
How do even know which multi-methods to implement?
Clearly the solution is quadratic in the number of cases.
In the pattern matching system that is manifest in the source,
and is managable because the collection of cases is a CLOSED type.
In the OO solution it is, and must be open, which means there's
no way to add new types incrementally. The OO way is to add
new methods with the types, which is linear.
linear doesn't fit into quadratic :)
> And the dispatcher would automatically determine the most specific match
> between the two objects.
How? Felix doesn't support any kind of subtyping: at best
there are some coercions (throw out some fields of a record
for example), but all that is handled at compile time.
> > Care needed: 'metaprogramming' is a bogus idea. It's a
> > way of giving up on what is really required: better
> > polymorphism.
> >
>
> I should have been a bit more clear. I meant the whole metaocaml-like
> quoting.
Yes. But that's a lame implementation of what is really required:
polyadic programming, aka higher order polymorphism.
Barry Jay claims to have solved this fully now, with
pattern matching calculus -- you can get his paper from
his web site or the Felix one. It's quite readable!
http://felix.sf.net/papers/purepattern.pdf
Basically we want
map f x
to work where f is a list, tree, or whatever.
In other words we want map to have a *single definition*
polymorphic over the data functor .. not just the type
of data stored in the data structure, but the data structure
itself. Not overloading. Not C++ templates. Not even
STL which is one of the best approximations to a solution
available .. STL iterators generalise for several classes
of sequential data structures!
Ditto for 'fold'.
People use 'generic' programming or 'staged evaluation' or
'partial evaluators' or 'meta-programming' and even
'dynamic typing' to try to make this work.
It is all known to be wrong. It is all hacks to get closer
to what is REALLY wanted: polyadic programming.
> True. However, llvm also can generate c code, which could be a nice stopgap.
But I don't think it is worth it -- it need to generate native
code for all commonly available processors or it is useless.
Or ..
> I was actually thinking of llvm's bytecode and interpretation.
That's a possibility. The problem is .. we'd have to build
llvm which is itself a major toolkit. That's a bit scary at the
moment :)
--
John Skaller <skaller at users dot sf dot net>
Felix, successor to C++: http://felix.sf.net
-------------------------------------------------------------------------
Using Tomcat but need to do more? Need to support web services, security?
Get stuff done quickly with pre-integrated technology to make your job easier
Download IBM WebSphere Application Server v.1.0.1 based on Apache Geronimo
http://sel.as-us.falkag.net/sel?cmd=lnk&kid=120709&bid=263057&dat=121642
_______________________________________________
Felix-language mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/felix-language