> The function "unsafePerformIO" is not a hack, it is the tool that allows you to write safe functions with the correct, pure type signature even though the compiler cannot prove that the function is safe.
It is a hack, since it subverts the type system. It allows you to write safe functions with a pure (and potentially lying) type signature, but it also has no problem letting you create completely unsafe and broken functions.
> The resulting output has type "a -> IO b", but it doesn't actually do IO and it has no side effects!
Of course it does in its implementation, you do have to fill the memoization cache on a miss don't you?
> The "unsafePerformIO" function is a non-hack used by careful programmers to expose pure interfaces to code that uses impure constructs.
I don't agree with the first part of your declaration. At all.
> Of course, unsafe does mean unsafe... you can easily cause segfaults with that thing, you have to use it correctly.
And that's why it's a hack, just as using bit shifting instead of multiplication or division is a hack as it relies on the implementation details of the language and the hardware infrastructure. Yeah careful programmers can use it to wring out the latest drop of performance out of their software (assuming there is no optimizing compiler on the platform), but it's still a hack.
It seems to me that there is an element of hypocrisy in some of the complaints above; it is as if they were saying:
> In Haskell, it's a nightmare to define a pure function with IO. You have to use that dreadful hack `unsafePerformIO`! In practical languages, by contrast, we are spared this boilerplate, since basically every line is already unsafePerformIO.
> It seems to me that there is an element of hypocrisy in some of the complaints above; it is as if they were saying
Apart from the "nightmare" part, this statement you made up happens to be factually true. What is your issue with it? It's exactly what happens: in most other langages, every line is indeed unsafePerformIO. Isn't that fact one of the reasons Haskellers give for using haskell in the first place?
We use Haskell so that 99% of the time, the compiler can prove our program safe. Then, the other 1% of the time, we use our human intuition to decide to "gamble" and disagree with the compiler.
In most languages, 100% of your code is that same gamble.
let x = [1..]
in do print (x !! 1000000)
print (x !! 1000000)
Element #1000000 (counting from zero) of the list "x" is printed out twice. The first time, "x" is a thunk. That thunk is evaluated, and the runtime stores the resulting value back into "x". The second time, "x" is a constructor, so it does not need to be evaluated. You'll see the memory usage spike after the first "print" to account for the million cons cells allocated.
This is no different than the interface provided by the memoization function. What distinguishes pure from impure is not memory access -- memory MUST always be modified in order to perform calculation. I recommend reading the Haskell report section on semantics.
It is a hack, since it subverts the type system. It allows you to write safe functions with a pure (and potentially lying) type signature, but it also has no problem letting you create completely unsafe and broken functions.
> The resulting output has type "a -> IO b", but it doesn't actually do IO and it has no side effects!
Of course it does in its implementation, you do have to fill the memoization cache on a miss don't you?
> The "unsafePerformIO" function is a non-hack used by careful programmers to expose pure interfaces to code that uses impure constructs.
I don't agree with the first part of your declaration. At all.
> Of course, unsafe does mean unsafe... you can easily cause segfaults with that thing, you have to use it correctly.
And that's why it's a hack, just as using bit shifting instead of multiplication or division is a hack as it relies on the implementation details of the language and the hardware infrastructure. Yeah careful programmers can use it to wring out the latest drop of performance out of their software (assuming there is no optimizing compiler on the platform), but it's still a hack.