> > II) Use catch/throw for control structures, use rescue/raise for > > communicating errors. [...] > > catch (:done) do > > loop do > > # Note: prompt_and_read can throw :done > > first_name = prompt_and_read "First name" > > last_name = prompt_and_read "Last name" > > phone = prompt_and_read "Phone" > > > > myfile.puts first_name + "\t" + last_name + "\t" + phone > > end > > end > > Well, that's interesting! (I didn't knew this is possible.) > What would happen in case there's no :done in the caller? > The longer I think about it the more I like it. I'm afraid I disagree. Usually, it's better to make exits from a loop explicit. Why is the comment ("# Note: prompt_and_read can throw :done") necessary? Because without it (and without examining the code of prompt_and_read), the reader of the code can't tell where and when the loop is exited. This design obliges the reader to rely on comments to get such important information as loop exits. I think it's a poor design, I'm afraid. I would write loop do first_name, last_name, phone = prompt_and_read "First name", "Last name", "Phone" or break .... end or something along the lines. (Have I got the precedence of operators correct? If not, please add a pair of parens.) If you add a comment on what prompt_and_read does, so much the better. But, comments are unnecessary because returning nil on failure is a common idiom. So I disagree with the general statement "Use catch/throw for control structures", although I'm sure there are cases where catch/throw as a control structure is a good solution. I would say, "Use raise/rescue for communicating errors, use catch/throw sparingly." Or if you can formulate cases for legitimate use of catch/throw, please replace "sparingly" with your phrase. My 2 yen (about 1.7 US cents). Cheers, Ryo