DDC compiler and effects; better than Haskell? (was Re:
[Haskell-cafe] unsafeDestructiveAssign?)
Robin Green
greenrd at greenrd.org
Tue Aug 11 20:16:56 EDT 2009
On Wed, 12 Aug 2009 08:34:28 -0500
Derek Elkins <derek.a.elkins at gmail.com> wrote:
> On Tue, Aug 11, 2009 at 3:51 PM, Robin Green<greenrd at greenrd.org>
> wrote:
> > On Wed, 12 Aug 2009 11:37:02 +0200
> > Peter Verswyvelen <bugfact at gmail.com> wrote:
> >
> >> Yes, sorry.
> >>
> >> But I think I already found the answer to my own question.
> >>
> >> DDC functions that are lazy don't allow side effects:
> >> http://www.haskell.org/haskellwiki/DDC/EvaluationOrder
> >>
> >> Anyway it would be cool if the DDC EffectSystem would also work on
> >> lazy functions :)
> >
> > As was just pointed out in the unsafeDestructiveAssign thread from
> > which this thread was forked, effects are incompatible with
> > non-strict evaluation.
>
> No, they aren't. At least, they aren't in any technical way. There
> have been more than a few languages supporting both laziness and
> mutation starting with Algol.
OK, explicitly creating thunks, like in Algol, LISP and CAL, can work,
because you can either prevent the programmer from using mutation
inside a thunk (as in the CAL approach), or rely on the programmer to
ensure that mutations are only done in a safe order (as in the
"callback as thunk" approach, which can be done in almost any impure
language).
But if almost *every* expression is a thunk, as in a non-strict
language like Haskell, and if moreover evaluation order can differ
depending on the compiler/interpreter, or compiler version, or compiler
flags, it becomes impractical to combine them. So yes, I agree, it's
not an absolute technical incompatibility, it's a practical one.
> > Also, effects would destroy modular reasoning.
>
> Again, it is purity, not laziness, that allows compositional
> reasoning. Effects destroy compositional reasoning in a strict
> language just as much.
Not really - in a strict language, if in method M action A always
happens before action B, then that fact will remain true in whichever
context M is called (ignoring threading issues). In a non-strict, impure
language, assuming monads are not used, if you have a function f which
performs actions A and B, and two other functions g and h which both
call f, the actions could happen in one order in g, and in the opposite
order - or not at all - in h, because of a difference in data demanded
by each function. Indeed, unless g and h are "top-level" functions (in
the sense that they are main functions or invoked from some
ghci-equivalent) the notion of "the" order the actions are performed in
is ill-defined, because it could vary depending on which function g or
h is being called from.
Now, you could say, the strict order of evaluation can be simulated in
a non-strict language on a case-by-case basis by using monads or
whatever. Well, yes, but that would be missing the point, because the
original point of this discussion was to avoid having to use monads.
--
Robin
More information about the Haskell-Cafe
mailing list