Rules to Better Code Commenting

​Rules for adding comments to code.​

Hold on a second! How would you like to view this content?
Just the title! A brief blurb! Gimme everything!
  1. Comments - Do you add a comment when you use Thread.Sleep?

    ​​​First don’t do it but if you have to add a delay to the process, it should always be commented – as though your life depended on it.​ 

    public DialogResult RefreshSchema() {
        SSW.SQLAuditor.WindowsUI.QueryAnalysisForm.RunScript(Startup.PageQueryAnalyzer.txtScript.Text)
        System.Windows.Forms.Application.DoEvents()
        // This is a sleep to delay the Application.DoEvent process 
        System.Threading.Thread.Sleep(500)
        System.Windows.Forms.Application.DoEvents()
        ...
    }​

  2. Comments - Do you add comments for your code if it is updated?

    ​​​​​​It's also important that you have a consistent code comment for your updating, which can be used by other developers to quickly determine the workings of the updating.​​

    Example of commenting a method, it is strongly recommended that you add an adequate comment for your updating.

    private void iStopwatchOptionsForm_Resizing(object sender, System.EventArgs e) {
        if (this.WindowState = FormWindowState.Minimized) {
            this.Hide()
        }
    }

    Figure: Bad example in VB.NET

    //
    // Commented - we don't need to hide this from when it is minimum size, just leave it on taskbar.
    // FW, 11/01/2018
    //
    private void iStopwatchOptionsForm_Resizing(object sender, System.EventArgs e) {
        if (this.WindowState = FormWindowState.Minimized) {
            this.Hide()
        }
    }

    Figure: Good example in VB.NET

    private void iStopwatchOptionsForm_Resizing(object sender, System.EventArgs e) {
        // ​Don't close this form except closing this application - using hide instead;
        if (!this.m_isForceClose) {
            if (this.IsOptionsModified) {
                if (MessageBox.Show("Do
    you want to save the changes?", Me.GetApplicationTitle, MessageBoxButtons.YesNo,
    MessageBoxIcon.Warning) = DialogResult.Yes) {
                    this.SaveOptions()
                }
            }
        }
    }

    Figure: Bad example in VB.NET

    private void iStopwatchOptionsForm_Resizing(object sender, System.EventArgs e) {
        // Don't close this form except closing this application - using hide instead;
        if (!this.m_isForceClose) {
            // <added by FW, 11/10/2006>
            // Remind saving the changes if the options were modified.
            if (this.IsOptionsModified) {
                if (MessageBox.Show("Do
    you want to save the changes?", Me.GetApplicationTitle, MessageBoxButtons.YesNo,
    MessageBoxIcon.Warning) = DialogResult.Yes) {
                    this.SaveOptions()
                }
            }
            // </added>
        }
    }

    Figure: Good example in VB.NET ​
  3. Comments - Do you comment each property and method?

    ​​​It's important that you have a consistent code comment standard throughout an application, regardless of language. Therefore, other developers can quickly determine the workings of a function/sub/class/stored procedure. Ideally, the code should be as simple and self-explanatory as possible.

    UPDATE: See Robert Martin Chapter 4: Comments  Clean Code: A Handbook of Agile Software Craftsmanship

    E.g. catch (InteropServices.COMException ex) //Catch all COM Exceptions from third-party COM component

    In JavaScript and HTML, you should put these comments between the 
    <HEAD> and </HEAD>
    tags. 

    To delimit the comments (ie top and bottom), you should use the standard block comment markers of 
    <!-- and -->. 

    A CSS file should be delimited with the block comment marks of ​​
    /* and */.

    If the file contains any function/sub module/class declaration, comments will be contained​​ to each of them containing at least the following:

    • function/sub module/class name
    • role of the function/sub module/class declaration

    Above a method or property declaration:

    /// <summary>
    /// 
    /// </summary>
    /// <param name="sender"></param>
    /// <param name="e"></param>
    /// <remarks ></remarks>

    ​Bonus - you can automatically generate documentation - but the number of clients that want this is minimal.


  4. Comments - Do you create Task List Comments for your code?

    ​​Task List comments can be used to indicate a variety of work to be done at the location marked, including:

    • features to be added;
    • problems to be corrected;
    • classes to implement;
    • place markers for error-handling code;
    • reminders to check-in the file.

    As with other Task List entries, you can double-click any comment entry to display the file indicated in the Code Editor and jump to the line of code marked. More details for Task List comments.

    asd

    task-list-eg-1.png

    ​​Figure: Bad example - the comment doesn't show in Task List window
    task-list-eg-2.png
    Figure: Good example - Marked TODO in the comment, so you can see it in Task List window and double-click to jump to​
    task-list-eg-3.png
    Figure: Good example - Marked HACK in the comment, so you can see it in Task List window and double-click to jump to

  5. Comments - Do you follow the general commenting rules?

    ​​There is almost always a better alternative to adding comments to your code.
    What are the downsides of comments? What are the alternatives? What are bad and good types of comments? 


    There is almost always a better alternative to adding comments to your code.
    (Chapter 4: Comments, Clean Code is a treatise par excellence on the topic.)

    What are the downsides of comments?

    1. Comments don't participate in refactoring and therefore get out of date surprisingly quickly.
    2. Comments are dismissed by the compiler (except in weird languages like java) and therefore don't participate in the design.
    3. Unless strategically added, they place a burden on the reader of the code (they now have to understand 2 things: the code and your comments).

    What are the alternatives to comments?

    1. Change name of the element (class, function, parameter, variable, test etc.) to a longer more apt name to further document it.
    2. For ‘cryptic’ code (perhaps to optimize it), rewrite it in simpler terms (leave optimization to the runtimes).
    3. Add targeted unit tests to document a piece of code.
    4. Innovative techniques that are well known solutions to common code smells e.g.:
      1. For large methods/classes, break them and have longer names for them.
      2. For a method with large number of parameters, wrap them all up in a Parameter Object.
      3. <pair up with someone else, think… be creative.>
    What some *bad* types of comments?
    1. That explain the "what"/"how" of the code. Basically the code rewritten in your mother tongue.
    2. Documentation comments in non-public surface area.
    3. Commenting out the code itself (perhaps to work on it later? That’s what source control is for).
    4. TODO comments (Little ones are OK, don't leave them there for too long. The big effort TODOs - say that are over an hour or two - should have a work item URL to it).
    5. And many more…
    What some *good* types of comments?
    Very few of these really. Although even these are subject to all the downsides of comments.
    Note that a lot of punch can be delivered in 140 characters! Twitter previously?
    1. Comments that explain the why (e.g. strategic insights).
    2. … that hyperlink to an external source where you got the idea/piece of code.
    3. … that hyperlink to a Bug/PBI for adding some context.
    4. … that are documentation comments for your next-biggest-thing-on-Nuget library.
    5. … that are real apologies (perhaps you had to add some gut-wrenching nasty code just to meeting time constraints, must be accompanied by a link to Bug/PBI).


    Last but not the least, some parting words from @UncleBob himself:
    "A comment is an apology for not choosing a more clear name, or a more reasonable set of parameters, or for the failure to use explanatory variables and explanatory functions. Apologies for making the code unmaintainable, apologies for not using well-known algorithms, apologies for writing 'clever' code, apologies for not having a good version control system, apologies for not having finished the job of writing the code, or for leaving vulnerabilities or flaws in the code, apologies for hand-optimizing C code in ugly ways."
    - Uncle Bob (Robert Martin of 'Clean Code' fame)


  6. Comments - Do you know what to do with comments and Debug.Print statements

    ​​When you create comments in your code, it is better to document why you've done something a certain way than to document how you did it. The code itself should tell the reader what is happening, there's no need to create "how" comments that merely restate the obvious unless you're using some technique that won't be apparent to most readers.

    ​What do you do with your print statements? Sometimes a programmer will place print statements at critical points in the program to print out debug statements for either bug hunting or testing. After the testing is successful, often the print statements are removed from the code. This is a bad thing to do. Debugging print statements are paths that show where the programmer has been. They should be commented out, but the statements should be left in the code in the form of comments. Thus, if the code breaks down later, the programmers (who might not remember or even know the program to start with), will be able to see where testing has been done and where the fault is likely to be - i.e., elsewhere.

    private void Command0_Click() {
        rst.Open("SELECT * FROM Emp") // Open recordset with employee records
        // Exit sub if the count is greater than 1,000
        if (intCount > 1000) {
            return
        } else  {
        .....processing code
    }

    Bad Example​

    private void Command0_Click() {
        rst.Open("SELECT * FROM Emp")
    ​    // Count will exceed 1,000 during eighteenth century
        // leap years, which we aren't prepared to handle.
        if (intCount > 1000) {
            return
        } else  {
        .....processing code
    }

    Good Example