This is a question that was put to me many years ago as a gradute in a job interview and it's nagged at my brain now and again and I've never really found a good answer that satisfied me.

The interviewer in question was looking for a black and white answer, there was no middle ground. I never got the chance to ask about the rationale behind the question, but I'm curious why that question would be put to a developer and what you would learn from a yes or no answer?

From my own point of view, I can read Java, Python, Delphi etc, but if my manager comes up to me and asks me how far along in a project I am and I say "The code is 80% complete" (and before you start shooting me down, I've heard this uttered in a couple of offices by developers), how exactly is that self documenting? Apologies if this question seems strange, but I'd rather ask and get some opinions on it to gain a better understanding of why it would be put to someone in an interview.

As it currently stands, this question is not a good fit for our Q&A format. We expect answers to be supported by facts, references, or expertise, but this question will likely solicit debate, arguments, polling, or extended discussion. If you feel that this question can be improved and possibly reopened, visit the help center for guidance.
If this question can be reworded to fit the rules in the help center, please edit the question.

6

I don't learn from a yes or no answer, I learn from asking a black or white answer to such a question. My answer would be no. To the job.
–
mouvicielFeb 14 '11 at 21:10

11

Not sure I get your question, "self documenting code" typically describes well written and easy to understand (the intention of) code, not really related to progress AFAIK... Some developers use this approach rather than commenting code...
–
NimFeb 14 '11 at 21:10

1

@Nim - more often in addition to comments etc, but +1 that comment.
–
Steve314Feb 14 '11 at 21:14

1

@ Nim, I've seen different definitions for what "self documenting code" means, but the way the question was put to me, it translated in my head as "Can you look at any code out there and understand everything you need to know just by looking at the code?", maybe I'm complicating this, but If it was ever put to me again, I dunno exactly how I would answer it. That's what gets to me.
–
Desolate PlanetFeb 14 '11 at 21:21

16 Answers
16

Partially.

Code that uses Big English Words can be partially self-documenting in that the names for all the functions and variables can tell you what it is doing. But it probably won't tell you why.

Compare:

a->b;
# what is b doing? what is the a object?
carEngine->startIgnition;
# much more clear what objects are involved

But you still don't know why a car is being started. Hence, only partially. It's kind of terrible that your interviewer was expecting a black and white answer, unless his view of black and white included a very strong maybe.

+1 Code that explains what is happening may still not explain why it's happening that way (and not some other way).
–
FrustratedWithFormsDesignerFeb 14 '11 at 21:17

23

+1 I believe that is the best definition for what self-documenting code should do vs what comments should do. Code should always tell you clearly 'what' and comments should tell you 'why'.
–
Dan McGrathFeb 14 '11 at 21:26

9

You're missing the key: Code that clearly explains what is happening will also clearly explain why to a reader with domain knowledge of the task being performed. This is why, in my code, I don't usually write comments--those who care enough to read the code will know what it's supposed to be doing anyway and thus already have the "why"--but when I'm doing something that looks unusual or arbitrary I'll put in a comment explaining why it's necessary.
–
Mason WheelerFeb 14 '11 at 22:36

5

@Mason, not necessarily. For instance, if you have a place that needs a sorting algorithm, and there is a very clear and easily understandable implementation of Selection Sort, but you have no indication what so ever of WHY this was needed instead of just using the default sort routine in the runtime library? (it then turned out that swapping two items is very expensive and Selection Sort only needs n swaps, and most other uses more...)
–
user1249Feb 14 '11 at 23:02

4

You would know why the car was being started if that statement was in function called InitiateCommuteToWork() or StartPreRaceSequence().
–
PemdasFeb 16 '11 at 1:11

If they insist on a black and white answer with no middle ground allowed, the answer is no.

The more complete answer is that code should be self-documenting to the maximum extent that's reasonable, but there's no reasonable way to include some types of documentation in the code. Just for example, the code might do a fine just of documenting what information is collected on form A, what in form B and what on form C. It generally won't (and probably shouldn't) attempt to document tests showing that dividing the data up in that way reduced errors x% compared to (for example) using only two forms instead of three.

Anything but the most trivial piece of code can benefit from at least some outside documentation.

My answer. To the greatest extent possible, you should strive to make your code as self-documenting as possible. There are many reasons for this. When initially written, an average of one line in 10 has a mistake. Mistakes in code tend to be found and fixed. Mistakes in documentation tend to be left. And in maintenance it is common for code and documentation to drift apart.

That said, there are limitations to what can be done by making code clear. In those cases, you must document.

What about the case where you have the choice about documenting? My view is that maintenance depends strongly on your organization. If you have excellent software developers and a rigorous code review process (as, for instance, Google does), then your process and people can be such that you don't need to be as concerned about comments failing to be maintained. In that case a much more comment-heavy style makes a lot of sense. (Google does, in fact, have a comment-heavy style.) However if you have a more typical organization then I'm going to heavily distrust any comments that I see, and I'm going to hope that you had people that believed in trying to make code self-documenting. In that situation I'll regard comments as superfluous.

For an interesting conversation on the merits and disadvantages of commenting, see http://www.perlmonks.org/index.pl?node_id=65153 for an old conversation I was part of. (Note, at the same time we had that conversation, there was a private set of chats that were friendlier. I have always regretted that only the more negative half of the conversation is public.) My opinions no longer exactly match what I thought then, but I still think that the conversation has worthwhile food for thought.

+1 for "mistakes in documentation tend to be left", though that really doesn't go far enough. It's more like "mistakes in documentation aren't noticed until years later when someone notices that they don't match the code".
–
Larry ColemanFeb 14 '11 at 23:04

I find that this question comes up a lot, and often has a religious fervor about it. Here is my take on it...

In an ideal world the following statement could be made:

Code should be written in such a way, that the logic can be followed without needing commenting.

OK, this is fair enough, but the problem is that we don't live in an ideal world. There are some issues with achieving this ideal statement.

Programmers are often not the experts in the industry they are programming against. It's easy enough to understand a function such as startEngine(Car car) (most) everyone can understand what is being asked here. But move to the real world, and things get a little fuzzier. For example the function getSess(String tid, String aid) would be perfectly understandable to a transport engineer who understood DWDM systems, but it can present a challenge to the new programmer just put on the project. Well placed comments can help ease the transition to understanding the code in a timely manner.

Programmers asked to maintain the code are often not as skilled as the original architects of the code. The original programmer may have been skilled enough to write a fast, succinct, efficient algorithm to accomplish a specific task. But the programmer tasked to maintain that code may struggle with trying to understand what is going on. Well placed comments can help ease the transition to understanding the code in a timely manner.

How many times have you written a bit of code, that you later struggled to understand why you did that, or even what you were trying to achieve? We all do that from time to time. Solving a problem, and producing a easy to follow solution to a problem are often two different mindsets. Unless you are the person that can write code perfectly out of the gate, you often make a lot of missteps with your code as you go along. You may also may not be able to get back to this bit of code for awhile. Well placed comments can help ease the transition to understanding the code in a timely manner.

Unique situations require explanation. For example a programmer may wonder why a 100ms pause was put into a bit of code communicating with a DWDM device. Letting the next programmer know that a pause is needed because the device is slow on the uptake, and may miss the command would be a valuable bit of information to have. Well placed comments can help ease the transition to understanding the code in a timely manner.

Nicely written, "self-documenting" code is a joy to find. Nicely written, "self-documenting" code, with well placed, informative comments is a godsend, and a very rare find.

Yes, code is self-documenting. The variables, methods, and class names can all be made to be easy to read and understand so that this is a form of self-documenting. There may be something within the code style that gives XML documentation at the end that is considered standard procedure. In other words it is part of the developer's job to provide documentation that may be intermixed with the code.

No, code is not self-documenting. The business decisions made, design choices made, and other factors aren't going to appear in the lines of code and should be written down outside of the code base. Thus external documentation is necessary and these are examples of it.

Point of asking: Would you give a partial answer recognizing the limitations of an answer or would you blindly lean on to whichever side you believe is the better practice? How much conviction do you have in your answer if it is a yes or no? It could be seen as a stressful question that is designed to get a rise out of someone who may answer, "What the... ? That's the dumbest question you could ever ask me. I refuse to answer that on the grounds that it insults my intelligence beyond belief!" as a rather arrogant and pompous answer that I could picture some people giving an answer with that tone.

Usually self documenting code refers to the practice of using a naming convention for variables, functions, etc. such that the purpose of the code is self evident. So, no code by itself is not self documenting. I don't understand what you are referring to in the third paragraph. That seems to have nothing to do with self documenting code.

Jack Reeves made a compelling argument that code is design. As far as many are concerned the actual code is the only "document" that tells you what the system does. Everything else decays as a live system tends to drift further and further away from the designed system. Even if you were to generate a document from the code (like many UML tools can do nowadays), it's still only an accurate documentation of the system at that point in time.

So yes code is self-documenting. How well it's documented is another question alltogether.

As I've become more experienced, I've learned that the real answer is that the code plus the environment of the reader determines the level of self-documentation.

In order to minimize the variance between the reader's environment and the writer's environment, we add comments. The more comments needed, typically the less experienced the writer. There's a quite wonderful essay out there describing this aspect of software development, but I don't remember who wrote it or where I found it.

I know the answer most people expect to that question would be "no," but I'm going to say yes.
If I were asked this in an interview for a job, I would still say yes.

I've worked on a lot of different projects with open and closed source. They have ranged in documentation from simple comments left as programmer's notes to full API documentations. While API documentation can be great, I've always eventually reached a situation where written-language documentation was insufficient to determine the actual behavior of the code. I ended up looking at source code, reverse engineering the applications, or pestering developers with source access to look at the source code and specify further.

To me, the code is the ultimate documentation. No matter how much you write in words what a program is going to do, the exact behavior is defined by the code.

I agree that when writing code you should try to make your code as self describing as possible. However as others have mentioned it's almost impossible in a complex program to completely describe everything that the code is doing. I'm not against comments, in fact I find that with good comments it can be easier to read code, even though the code could explain itself without the comments reading English or some spoken language is almost always easier.

I've found that the most useful documentation is almost never comments. Most of the projects I've been working on recently have wiki's included that includes all the different parts, how they connect. I try to explain what was on my mind when I was writing the code so that other people will not break my code because they didn't understand the why. It can also help someone else refactor the code with more confidence. I often find myself hesitant to refactor code because i never know what it could break and there is no explanation. Even if you're the only person working on a project I guarantee in a year or two you'll forget why you did something even if its the most beautiful piece of code you can still forget why its there.

Sure, if you have unlimited time. I've spent 25+ years documenting code for other developers. My position has always been that I try to explain something so another developer can grok it in 5 minutes, when they could simply examine the code and figure it out in a half-hour. If I save everyone who looks at that method 25 minutes, then I've done my job.

I think that the class diagram should always be used to document the code. I don't think that if you look at code directly you can see the complete architecture. I agree that if you have written the code yourself or working on it for long time then you can understand but each time a new demand is arise each time you need to look at the code and search where to add this new code.

What we do in our company is to have class diagrams views of our project. We don't really spend time modeling but only use class diagram to visualize the code after a reverse engineering. If the code change then there is a merge mechanism and my class diagrams are always updated.

What is fantastic is to be able to add comments, constraints into the diagram in addition to java doc. We reverse the project, then create a model and finaly extract views from the model displayed as UML class diagrams. I don't code at this stage but get a blue print from code architecture and work on it to create or extend my current architecture. If I like it then I press a button and my existing code is merge with my diagrams. I mean merge and certainly not full code generation. Only the delta between existing code and my diagrams is written, not the full code each time.

I have been studding for many years, have a master degree and still code but I don't want just be a java writer and would like to use my brain a little more. UML views give me what I need in order to think about my architecture, communicate with the other team members and create better architecture without using Model Driven development but only the delta between existing manually written code and graphically create class diagrams. I create my architecture at code level, then reverse it and look at the model. I create views and try to improve my architecture directly in the code, then reverse again and see what is done etc...
It is a permanent iteration with no model driven code generation but live synchronization or merge between code and UML. What I like is that the code drives the UML and certainly not the opposite. UML class diagram is for me beautifier of my code and I like it !!