I <3 Steve McConnell*
Coding Horror
programming and human factors
by Jeff Atwood

September 22, 2005

In Defense of Verbosity

During the fantastic Monad session at PDC 2005*, Jeffrey Snover and Jim Truher illustrated the tradeoff between verbosity and conciseness:

cp c:\apples c:\oranges -fo -r

copy-item c:\apples c:\oranges -force -recurse

Monad has a ton of aliases for common commands (eg, echo is the same as write-object), and it's smart enough to disambiguate parameters if you type enough characters. You get to choose: do I want to be verbose, or do I want to be concise?

Even UNIX tools, which aren't exactly known for their user friendliness, typically offer both verbose and concise options. Consider the excellent wget utility as an example. What the heck does this mean:

wget -m -k -K -E http://www.gnu.org/ -o /home/me/weeklog

Who knows? It could be doing anything. But if we disambiguate with the verbose parameters...

wget --mirror --convert-links --backup-converted 
        --html-extension -o /home/me/weeklog
        http://www.gnu.org/

Suddenly it's quite plain what is happening.

People say VB.NET is too verbose like that's a bad thing. Is English too verbose? Would this post be easier to read in a court reporter's shorthand? Would it be easier to read if I dropped the vowels and the stopwords?

Compare this elegant, concise C# code..

            }
        }
    }

.. to its VB.NET equivalent:

            End Select
        End If
    End If

VB.NET has its problems, to be sure, but verbosity isn't one of them. Saving keystrokes while writing code is a fool's economy. Isn't that why we have these fancy IDEs? As Steve McConnell notes in Write Programs for People First, Computers Second, optimizing for conciseness is a poor tradeoff. Most code is written only once, but read dozens of times:

The computer doesn't care whether your code is readable. It's better at reading binary machine instructions than it is at reading high-level language statements. You write readable code because it helps other people to read your code.

Readable code doesn't take any longer to write than confusing code does, at least not in the long run. It's easier to be sure your code works if you easily read what you wrote. That should be a sufficent reason to write readable code. But code is also read during reviews. It's read when you or someone else fixes an error. It's read when the code is modified. It's read when someone tries to use part of your code in a similar program.

Making code readable is not an optional part of the development process, and favoring write-time convenience over read-time convenience is a false economy. You should go to the effort of writing good code, which you can do once, rather than the effort of reading bad code, which you'd have to do again and again.

The idea of writing unreadable code because you're the only person working on a project sets a dangerous precedent. Your mother used to say, "What if your face froze in that expression?" And your dad used to say, "You play how you practice." Habits affect all your work; you can't turn them on and off at will, so be sure that what you're doing is something that you want to become a habit. A professional programmer writes readable code, period.

Even if you think you're the only one who will read your code, in the real world chances are good that someone else will need to modify your code. One study found that 10 generations of maintenance programmers work on an average program before it gets rewritten (Thomas 1984). Maintenance programmers spend 50 to 60 percent of their time trying to understand the code they have to maintain, and they appreciate the time you put into documenting it (Parikh and Zvegintzov 1983).

The ethic Steve is promoting here isn't specific to any language, of course. But it certainly does skew the results in favor of verbosity-- if it's available.

* Which were evidently rated #3 right after Anders' two talks, so if you didn't go, you missed a great session!

Posted by Jeff Atwood    View blog reactions

 

« Everything you always wanted to know about Task Manager but were afraid to ask On the Death of the Main Menu »

 

Comments

So how do your ideas relate to Paul Graham's?
http://www.paulgraham.com/power.html

:)

Kartik Agaram on September 24, 2005 01:54 AM

Eh, I don't buy that. As far as I'm concerned the most readable code is the _shortest_ code that clearly conveys the intended meaning. Reading lots of text is itself an effort that inherently degrades readability.

Sure, reporter shorthand isn't more readable than plain English. But what about elaborate Victorian style, laden with adjectives and parentheses?

Or a code example: compare "2 + 2 = 4" to "Equals(Plus(Two, Two), Four)". The second is more verbose, ergo it's more readable, right? Didn't think so... the symbols in the first example are both clear and concise, which is the optimum case.

Chris Nahr on September 24, 2005 02:31 AM

>"Even if you think you're the only one who will read your code"

Looking at code you wrote more than two weeks ago is like looking at code you are seeing for the first time.

— Alzheimer's Law of Programming

mike on September 24, 2005 03:47 AM

Katrik, the way I read Graham's essay, he does not consider the difference between "}" and "End Function" a measure of conciseness:

"I think a better measure of the size of a program would be the number of elements, where an element is anything that would be a distinct node if you drew a tree representing the source code."

Furthermore:

"Ultimately, I think you have to go with your gut. What does it feel like to program in the language? I think the way to find (or design) the best language is to become hypersensitive to how well a language lets you think, then choose/design the language that feels best. If some language feature is awkward or restricting, don't worry, you'll know about it.

Such hypersensitivity will come at a cost. You'll find that you can't stand programming in clumsy languages. [...] someone used to dynamic typing finds it unbearably restrictive to have to go back to programming in a language where you have to declare the type of every variable, and can't make a list of objects of different types."

In fact, I have a hard time getting from the essay where exactly his complaints about Basic lie. In the first quote, he's basically (ha) saying that the use of syntactic sugar should not be counted toward the measure of verbosity. Yet he freely says that Basic is verbose. On what basis, then, if a) the number of elements is the same between, say, VB and C#, and b) if (second quote) VB permits dynamic typing, therefore reducing the verbosity of explicit declarations? Perhaps I'm missing something. That happens a lot, actually.

Chris, interestingly you're showing Basic-like syntax (algebraic) vs. Lisp-like syntax (nested functions), speaking broadly. Yet Basic is considered the more verbose language. Not here, though. So is Basic better than Lisp?

In C-like languages, the tertiary operator is definitely more succinct than the equivalent if() block. It compiles down to the same object code. Is it better? Does it make programming easier a) for the original programmer and b) for those who must maintain the code later?

mike on September 24, 2005 04:03 AM

> Reading lots of text is itself an effort that inherently degrades readability

Then it must be really hard to read, you know, English. I don't buy this. At all. We read so much text every day! Our brains are highly optimized for this task.

You're really talking about *unnecessary* code, which I agree is a bad thing. But it has nothing to do with my point about verbosity-- "}" vs "End If".

> the tertiary operator is definitely more succinct than the equivalent if() block

I think you mean the "ternary" operator (eg, IIf() in vb), but I agree. I hate it in both languages. It's a perfect example of trading off an utterly meaningless one time write-time savings against dozens of read-time comprehension penalties-- It Makes Me Think.

It's just a bad deal no matter how you slice it.

Jeff Atwood on September 24, 2005 06:07 AM

> So how do your ideas relate to Paul Graham's?

Paul's point is that high level dynamically typed languages (Perl, Lisp, Ruby, etc) can do more in fewer lines of code compared to your traditional static, strongly typed languages like C#, Java, etc.

It's really a different point than mine. I'm saying we should use plain, simple English instead of geek-speak when defining language keywords. Failing that, at least give us the option to be verbose or succinct as we please, as shown in my command line options examples.

On the other hand, .NET seems to be evolving towards dynamic languages at a fairly rapid rate, and that's a good thing!

C# 3.0, VB 9, and D/X/LINQ, the language features being added to .NET are influenced *heavily* by dynamic languages, eg:

http://www.interact-sw.co.uk/iangblog/2005/09/23/varisntobject

Jeff Atwood on September 24, 2005 06:18 AM

In all fairness, your C vs VB example is quite contrived since it is taken completely out of context and not indented at all.
if (true = isVBVerbose())
{
Console.WriteLine("Carpal Tunnel hurts.");
}
else
{
Console.WriteLine("Rubbish.");
}

If (true = isVBVerbose())

Console.WriteLine("Carpal Tunnel hurts.")

Else

Console.WriteLine("Rubbish.")
End If

There is a comparison that is more fair. In any case, if verbosity is great, perhaps the VB team should have called 'Else' 'Otherwise' since it reads more like English. I just don't buy it. Interestingly, Ruby (can any language conversation nowadays omit a Ruby reference?) uses 'end' for everything and it isn't at all confusing. It eliminates the need for the End If End While End Function etc. To me, this is a great middle ground.

Christian Romney on September 24, 2005 09:47 AM

No one seems to be buying anything!

:-)

mike on September 24, 2005 05:45 PM

>"I think you mean the "ternary" operator (eg, IIf() in vb)"

Dunno, Jeff -- the following is from MSDN (http://msdn2.microsoft.com/en-us/library/ms173145]):

"In C#, an operator is a term or a symbol that takes one or more expressions, called operands, as input and returns a value. Operators that take one operand, such as the increment operator (++) or new, are called unary operators. Operators that take two operands, such as arithmetic operators (+,-,*,/) are called binary operators. One operator, the conditional operator (?:), takes three operands and is the sole tertiary operator in C#."

mike on September 24, 2005 05:49 PM

>uses 'end' for everything and it isn't at all confusing.

Hear, hear. The compiler can certainly sort these things out, so why the extra terms?

(Sorry to clog up your comments, Jeff.)

mike on September 24, 2005 05:55 PM

> The compiler can certainly sort these things out, so why the extra terms?

Because our brains aren't compilers? Of course, there is a point of diminishing returns on both sides, but it's always better to err on the side of verbosity when possible.


> Dunno, Jeff -- the following is from MSDN (

I can find tons of references to "ternary operator" in google.

http://discuss.fogcreek.com/joelonsoftware/default.asp?cmd=show&ixPost=142517

To be fair, there are 2x as many google hits for "tertiary operator" (521k vs 260k) so I'm not sure which one is correct.

At any rate, they're a prime example of the false economy of trading write-time conciseness compared to readability, so whatever they're called, we can agree on that ;)

Jeff Atwood on September 24, 2005 08:51 PM

All this talk of language affordances makes me think of Ken Arnold's post, Style is Substance:
http://www.artima.com/weblogs/viewpost.jsp?thread=74230

He takes Python's use of whitespace defining block structure to a logical (perhaps absurd) extension.

To join in the fun I'd add to his list, making the use of uppercase characters in an identifier, and the tab character outside a literal, lexical errors. The formatting differences used to write code tend to be larger barriers to readability then the syntax of the langauge. VB is largely readable because much of the style is enforced by the language rules, rather than simply because it uses tokens with more characters. Also I imagine few VB users use vi, vim, emacs, edlin, etc. making editor consistency another big plus.

One other random point, I always wondered what Python did about tab vs spaces, and finally I looked in wikipedia and found out. They did nothing! http://en.wikipedia.org/wiki/Python_programming_language

"The whitespace thing has minor disadvantages. Both space characters and tab characters are currently accepted as forms of indentation. Since they are not visually distinguishable (in many tools), mixing spaces and tabs can create bugs that are particularly difficult to find (a perennial suggestion among Python users has been removing tabs as block markers—except, of course, among those Python users who propound removing spaces instead)."

To my mind that erases the goodness created by the design choice to make whitespace matter. You can write obfuscated Python by mixing tabs and spaces. Doh!

(Yes despite the evidence to the contrary, in my head, these are on topic. :-)

Steve Steiner on September 24, 2005 11:41 PM

Adequate programming is whatever consistently works for you.

If writing nearly-unreadable code works for you because you want to save a keystroke here and there, fine then, you go do your thing...

...Elsewhere.

I won't work with you. None of the people on my team will.

Documentation is the most important part of a program. Developer time is more valuable than any other resource.

So, if we can't tell at a glance what someone else's program does, or we can't tell exactly what a program written a year or two ago does, then it's useless to us. We do not have the time or the inclination to study programs again and again to rediscover their tasks.

Once compiled, the programs'll be plenty small and fast.

UNTIL they are compiled, the source code is intended for HUMANS to read. And it had better do a damned good job at that or we'll throw it out and replace it (and the developer that wrote it!)

Eric K. on September 26, 2005 10:41 AM

"ternary" means "comprised of three parts", "tertiary" means "the third in a series". Besides, K&R call it the "ternary operator".

I think the reference in the MSDN docs is a goof especially directly after they use "unary" and "binary". How about utiary and bitiary? =)

As for the Google results, try putting those terms in quotes and you get 68,100 versus 593, which seems more reasonable.

Entering "tertiary operator" into Wikipedia brings one to "Ternary Operator" which explains the root "arity" and mentions "tertiary" as an inaccurate usage.

I have always liked the iif() function since I first encountered it in dBase III+, but I think that in code as in prose, readability is a balance between brevity and verbosity each in its right place. Sometimes the latter comes after the comment symbol.

Todd on September 27, 2005 12:22 AM

Thanks for the clarification, Todd.

That's a Mortal Kombat style coding fatality! So Mike, consider your virtua spine ripped out.

Jeff Atwood on September 27, 2005 03:49 AM

Here's a write up of verbosity taken way too far:

http://daringfireball.net/2005/09/englishlikeness_monster

Michael Kohne on September 27, 2005 07:27 AM

Excellent:
--
But saying what you mean, in English, almost never “just works” and compiles successfully as AppleScript, and so to be productive you still have to understand all of the ways that AppleScript actually works. But this is difficult, because the language syntax is optimized for English-likeness, rather than being optimized for making it clear just what the fuck is actually going on.
--

Unambiguous, descriptive keywords (eg, not {) is one thing, but I don't think I'd ever advocate making a language out of English sentence structures.

We definitely want to "optimize for making it clear just what the fuck is actually going on" ;)

Jeff Atwood on September 27, 2005 12:55 PM

"Sure, reporter shorthand isn't more readable than plain English. But what about elaborate Victorian style, laden with adjectives and parentheses?"

While taking the point, it could also be noted that Victorian prose contains more detail and shades of meaning than modern styles.

It concerns me a bit that I find it harder to read Darwin than Sagan, because the implication is that people in Darwin's time had no trouble understanding him, which means I'm not as literate as they were.

Paul Coddington on October 4, 2005 12:14 AM

VB hurts my eyes to read.

C syntax is simple and elegant.

I really don't see where you feel that VB gains ANYTHING by substituting END in for braces.

MS is putting all of its money on C#, not on VB.

C# uses similar syntax, in this respect, to C, not to VB.

Justin on December 18, 2005 07:20 PM

I may be in the minority, but I love ?: and use it constantly in Java. It's perfect for null-checking, like so:

return (name==null?"%":name);
return (active==null?"0":active);

Ruby also has an operator exclusively for "assign only if variable is nil":

active ||= "0"

In my mind this is infinitely better than writing if/else's everwhere, but as Eric pointed out above, whatever works for you and your team is best.

Elliot N on August 14, 2006 06:59 AM

So, I came across this article because I am trying to come up with support for putting the smack down on one of my coders and getting him to stop using the ternary operator for everything.

I honestly had no idea that there was even a single coder who thought as I, let alone a group. (though I am a bit miffed that my "source is for humans, not machines" philosophy is not as original as I once thought)

Like pretty much anything in the universe, the issue comes down to approriate usage. The ternary operator is perfect for things like:

String myWords = "You have " + cntItems + cntItems < 0 ? "item" : "items" + "in your shopping cart."

(or the return statements above, THAT is what I call elegant code, as opposed to "how much disconnected crap can I jam on a single 399 column line??")

It is HORRENDOUS when there are 13 different things, several constructors, a method call or two, a cast and a kitchen sink all sandwiched in a ?:

Again, source is for humnas. Too often, it is used by humans to attept to display how crazy mad cool they are and as a result comes out being utterly useless.

Thanks for the great conversation.

J. on April 4, 2007 12:47 PM

Let's be honest- VB is for BASIC coders and C# is for C++/Java coders, it's that simple. I coded for years in C/C++ and Java so C# is my choice when I'm in the MS env.

Chris Henry on November 20, 2007 12:50 PM

I think this a real strawman argument. I'm moving from VBA (visual basic for applications) to VB.Net, and I find the verbosity somewhat appauling. I'm fine with "End If" and "End Select"--these add some readability. From my old days in C, I'm also fine with "}"--concision cumulatively saves much time and (eye) space without losing much; more elegant.

The problem I DO have is more with the whole new generation of verbosity--all of .NET, and others--as a result of classing everything, and burying every last function in some deep tree, and recasting the most basic functions into object orientation. I understand that thinking in terms of objects brings a certain fluidity of use between libraries. But I find it really disturbing that the most basic needs (e.g. string handling) have been converted to OO; it seems unnaturally rigid; verbose; a typing tax and a reading tax; and most of all, mental convolution.

I wrote a brief blog post on this topic here: http://www.cooltechblog.com/?p=51

I suppose I'll get over it, but it makes working in VB.Net seem a lot more work than something before all the classism (e.g. VB, VBA). There must be a better way...

Greg on January 31, 2008 04:30 PM

> and burying every last function in some deep tree,
> and recasting the most basic functions into object orientation

Oh, I always want to scream in horror when I have to write those int-to-short casts (among others). I understand the technical side (and I even agree), but hey... tons of casts make the code really unreadable.

Rodrigo on February 12, 2008 07:44 PM

There are a couple things stopping me from switching to C#, the major obstacle being that I use KNF style intention, yet C# forces me to use Allman style. I could just disable the auto-complete and get around it, but then why should I even use the IDE at all and just edit my code in vim or something instead?

My other main argument is that C# does not allow for integer expansion. Preventing a cast from Button to XmlNode is one thing, but when I can't do something like:

int16 plus_six(int16 n){
return n + 6;
}
int32 five_plus_six = plus_six(5);

When it works in Visual Basic?

Miff on February 13, 2008 12:16 AM







(hear it spoken)


(no HTML)




Content (c) 2008 Jeff Atwood. Logo image used with permission of the author. (c) 1993 Steven C. McConnell. All Rights Reserved.