
On 11-06-08 11:17 PM, Gregory Guthrie wrote:
So the implication of the rules: 1) all IO must start from the top level, and there is only one IO 2) you cannot extract anything from an IO
Seems to be that the whole program structure becomes a series of do... blocks, which is basically a sequential imperative looking style. The general advice of "Strive to keep as much of the program pure as possible" thus seems difficult.
Suppose you teach Java or C++ or any OOP, and you give out this basic homework to beginners: write a program to take two complex numbers from the user, then print their sum. You are assured to receive such flawed design: class complex { double r, i; public: complex() { cout << "please enter the real part:"; cin >> r; cout << "please enter the imaginary part:"; cin >> i; } } The urge to do I/O at all the wrong places is a born instinct. Humanity strives to organize programs (and articles) by stream of consciousness rather than by separation of concerns. Why do they ask the user in the constructor? Because that's where the editor cursor was when they remembered to ask the user. Similarly in Haskell, why do they read input in the data processing function? Because that's where the editor cursor was when they remembered to read input. This is universal to FP, OOP, IP, any P, with or without language restrictions. For people who organize programs by stream of consciousness, Haskell's separation of IO does not help, but SML's and C++'s non-separation does not help either. Nothing helps. Don't worry about them. For people who organize programs by separation of concerns, such as you and me: Haskell's separation of IO helps. This is what matters.