> I thought about this problem some more, and I have realized that the
> problem of nondeterminacy for Haskell exceptions would in fact be
> considerably worse that I had previously considered. The trouble is
> that in the general case the problem is not just that the choice of
> which exception is raised is nondeterministic -- instead, it would be
> much worse: the choice of whether you raise an exception or loop
> forever can be also be nondeterministic. This occurs because of
> expressions such as `0/0 + loop'. Or, to take a more realistic (and
> nasty) example, `f 0' where `f x = 1/x + g x' where `g x' happens to
> loop if `x' is zero.
I don't agree that this is a problem. If (g x) loops when x is zero
then you should jolly well test for that:
f x | x == 0 = raise "x is zero"
| otherwise = 1/x + g x
I simply don't think it's reasonable to comletely prescribe
the evaluation order of a lazy functional program.
At the moment, Haskell has the fiction that a divide-by-zero
exception and non-termination are the same value, i.e. bottom.
That allows us to say that the behaviour of
f x = 1/x + g x
is identical regardless of whether "+" evaluates its first
argument first or second. But we all know that the behaviour
in these two cases is quite different: one prints a message and
halts, and the other fails to terminate. So in this sense
the behaviour of Haskell programs is already non-deterministic.
The nice thing about the NDSet story is that it makes clear
precisely where the non-determinism occurs. Equational reasoning
is not impaired, nor is the implementation penalised. I think
it's a great idea.
So I appear to be in disagreement here with Alex, Amr, and Fergus about
the importance of being able to say precisely which exception is raised.
I'm quite content with knowing which *set* of exceptions can be raised.
Ha!
Simon