[Israel.pm] Some thoughts about the "Red Flags" Presentation
Shlomi Fish
shlomif at iglu.org.il
Sun Dec 20 15:48:49 PST 2009
Hi all!
I've been thinking of two things that Sawyer said in his Red Flags
presentation:
1. http://www.slideshare.net/xSawyer/red-flags-1683319
2. http://use.perl.org/~xsawyerx/journal/39230
3. http://use.perl.org/~xsawyerx/journal/38576
The first thing I've thought about was Sawyer's warning against using goto
statements. One needs to know a little history (including some less known)
when considering the old "Goto statement considered harmful" mantra. I've
provided a summary of it here:
http://discuss.fogcreek.com/joelonsoftware3/default.asp?cmd=show&ixPost=78092
Granted, Dijkstra wrote an article with this title, and many people agreed
with him, and it was the opening shot of the Structured Programming Wars.
However, the title was mutated to be memorable by his editor (based on older
"considered harmful" editorials), and Dijkstra never meant that GOTOs were
always harmful.
Moreover, some people have demonstrated that it is possible to do structured
programming with goto statements, and sometimes even better with them than
without them.
For example, Don Knuth wrote an article "Structured Programming Using Goto
Statements" (rumouredly sub-titled "'Goto Statement Considered Harmful'
Considered Harmful") in which he deomnstrated exactly that. And I take this
view as well.
In Perl I found little motivation to use goto so far, and usually did not have
the need to in production code. But in non-C++ C (did not do a lot of C++ or
ObjC) I found it to be a useful tool especially for the cleanup-on-failure
pattern or to emulate Perl's "last LABEL" or "next LABEL".
{
.
.
.
ptr1 = malloc(...);
if (! ptr1)
{
goto cleanup;
}
ptr2 = malloc(....);
if (! ptr2)
{
goto cleanup;
}
/* More stuff. */
.
.
.
cleanup:
if (ptr2)
{
free(ptr2);
ptr2 = NULL;
}
if (ptr1)
{
free(ptr1);
ptr1 = NULL;
}
}
Sawyer later gave the argument that using goto was equivalent to using a jump
in a conversation. However, when talking we use different conventions from
when writing code, and we could say "do as I told you earlier" or "go to step
6" in conversation or writing. And what are the conversation equivalents of
loops, subroutines, closures, coroutines/continuations, object inheritance,
etc. and other thing we use in code? So it's not a right analogy.
Sawyer also gave a similar argument for criticising this construct which I
tend to like:
<<<<
if (...)
{
# do nothing
}
else
{
.
.
.
}
>>>>
(I'm flattered he read my code.)
He claimed that putting an empty block was equivalent to a pause when saying
"If the door is locked [pause]". However, it is equivalent to "If the door is
locked do nothing - you're set", because we as humans don't interpret empty
blocks, but can understand a "do nothing" imperative.
Recently I've ran into the following code:
<<<<
my $var = ...;
while ($line = ....)
{
if (($var) = ($line =~ m{(...)}....
{
# Do nothing
}
else
{
die "Could not match var in line '$line'."
}
}
>>>>
And I prefered to keep it this way because I was not sure of the !~
implications. (Though now that I think of it, I could have used if (!(($var) =
...).
This is what I had to say.
Regards,
Shlomi Fish
--
-----------------------------------------------------------------
Shlomi Fish http://www.shlomifish.org/
"Star Trek: We, the Living Dead" - http://shlom.in/st-wtld
Bzr is slower than Subversion in combination with Sourceforge.
( By: http://dazjorz.com/ )
More information about the Perl
mailing list