CS Coding Standards Full

Download as pdf or txt
Download as pdf or txt
You are on page 1of 41

Systems & Projects Governance

C# Coding Standards

Prepared By: Christian Maslen


Version: 0.1 (DRAFT)
Date: Date Published
C# Coding Standards

Distribution List:

Dallas Kidd
Alistair McElligot
James Mah
Stephen Lum
AHF Development Team

Document Acceptance:

Dallas Kidd Stephen Lum

Technical Manager AHF Manager Systems and Projects

Position or Title Position or Title


Name Name

An original document carries original signatures on this page. Photocopies may be out
of date. Please refer to the Project Office Manager for the latest version.

C#_Coding_Standards__Cover.doc CONFIDENTIAL Version 0.1 (DRAFT)


C# Coding Standards

Table of Contents

1 Introduction
1.1 Background
1.2 Document Purpose
1.3 Scope
1.4 Document Structure
1.5 Document Key
1.6 References
2 File Organisation
2.1 Solution Files
2.2 Project Files
2.3 C# Source Files
2.4 Using Directive
2.5 Directory Layout
3 Layout
3.1 Objectives of Good Layout
3.2 Braces and Parentheses
3.3 Indentation
3.4 Spaces
3.5 Line Length
3.6 Line Breaks and Long Statements
3.7 Line Spacing or Grouping
3.8 Laying Out Classes and Interfaces
3.9 Using Regions
3.10 Laying Out Comments
4 Naming Conventions
4.1 Capitalisation Styles
4.2 Naming Guidelines
5 Declarations
5.1 Number per Line
5.2 Initialisation
5.3 Placement
5.4 Attributes
6 Statements
6.1 Simple Statements
6.2 Return Statements
6.3 Break Statements
6.4 If, if-else, if else-if Statements
6.5 For / Foreach Statements
6.6 While/do-while Statements
6.7 Switch Statements
6.8 Try-catch statements
6.9 Properties and Indexers

C#_Coding_Standards__Cover.doc CONFIDENTIAL Version 0.1 (DRAFT)


C# Coding Standards
7 Comments
7.1 Implementation Comments
7.2 Documentation Comments
7.3 Special Comments
7.4 Header Comment
8 Programming Practices
8.1 Visibility
8.2 No “Magic” Variables
8.3 Refactoring
8.4 Unit Testing
8.5 Level of Abstraction
8.6 Defensive Programming
8.7 Use a variable for one purpose

Annexes

A Developer Environment Settings

B Standard Code Review Checklist

C Change History

C#_Coding_Standards__Cover.doc CONFIDENTIAL Version 0.1 (DRAFT)


C# Coding Standards

1 Introduction
1.1 Background
Coding standards promote consistency with arbitrary decisions such as indentation width or
how to format a comment. This consistency frees the developer from having to make these
decisions (often differently to any other developer on a given project) in every case.
Coding standards also help promote readability in programs. Readability has a positive
affective on the following aspects of a program:
a) Comprehensibility
b) Reviewability
c) Error rate
d) Debugging
e) Modifiability
f) Development time
g) External quality

1.2 Document Purpose


This document aims to provide C# coding standards for all .Net projects developed by Vero
Systems and Projects.

1.3 Scope
This document is limited to discussing C# coding style and standards. It does not address
architectural or design standards relating to C# programs. See
http://vsp/trac/val/wiki/ApplicationDesignStandards for the most current document
addressing design standards.

1.4 Document Structure


a) Chapter 1, Introduction
b) Chapter 2, File Organisation
c) Chapter 3, Layout
d) Chapter 4, Naming Conventions
e) Chapter 5, Declarations
f) Chapter 6, Statements
g) Chapter 7, Comments
h) Chapter 8, Programming Practices
i) Annex A, Develop Environment Settings
j) Annex B, Standard Code Review Checklist
k) Annex C, Change History

1.5 Document Key


1.5.1 Symbols
Symbols used throughout this document:

C#_Coding_Standards_CH01.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 1 - Page 1 of 2
C# Coding Standards

Symbol Description
→ Tab character
▫ Space character
[<stuff>] <stuff> is optional
<stuff> <stuff> is mandatory

1.5.2 Conventions
Conventions used throughout this document:
Courier New will be used to represent code

Code blocks will be bordered and shaded with 15% grey


If a piece of text is being highlighted within a code block it will be shown in
bold

1.6 References
EXPERT03 - Coding Standards and Guidelines for Visual C# .Net (Infosys).
KRÜGER 03 - C# Coding Style Guide for ICSharp by Mike Krüger.
MCCONNELL04 Code Complete Second Edition by Steve McConnell
ROBERTS05 - Article on How to setup a .Net Development Tree by Mike Roberts.
FOWLER99 – Refactoring: Improving the Design of Existing Code by Martin Fowler.

C#_Coding_Standards_CH01.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 1 - Page 2 of 2
C# Coding Standards

2 File Organisation
2.1 Solution Files
All solution files for a project are to reside in the following folder:
<SourceControlRoot>\<ProjectRoot>\Source\SolutionFolder\<SolutionFileName>
Where:
a) SourceControlRoot is the root folder for your source control package. Eg SvnRoot for
the Subversion root or VSSRoot for the Visual Source Safe root.
b) ProjectRoot is the root folder for your project. Under this will also be your
documentation, tools used on the project etc.
c) Source\SolutionFolder is always used as your Solution root folder. There will be a
solution per unit of unrelated functionality. For example, one folder may contain the
database solution while the other contains the application solution. This structure will
be defined per project by the technical lead.
d) SolutionFileName is the name of your solution file name. At a very minimum all
projects will have a solution file called [ProjectName]Master.sln (Master.sln is also
fine). This solution file will contain all .Net projects including setup and deployment
projects. If the solution has enough projects, smaller sub-solutions can be created that
only included the co-dependant projects.

2.2 Project Files


Never place a project file in the same folder as a solution file. The file should always be one
level down from the solution file, thus making the folder structure correspond with the
namespace structure.
Project files are named as per the target assembly name including the root namespace of
“Vero”. Assembly naming is discussed in section 4.4 of the .Net Application Design Standards
document.
Unit test projects are to be named identically to the project being tested with a “.Tests”
suffix.

2.3 C# Source Files


Source files names must correspond with the name of the entity being defined with the “.cs”
extension. It then follows that a source file only contains a single definition per file.
Creating files with multiple class definitions makes classes difficult to find using the solution
explorer or file explorer. This forces developers to use the less obvious Class Viewer to find a
source file. It also increases the likely hood of multiple developers needing to edit the same
file at the same time.
Never place assembly level attributes in a class file. The AssemblyInfo.cs file should be the
only place Assembly level attributes are defined. The exception to this is if all assemblies
within a project share Assembly level attributes such as the version number or the company
information. In this case common assembly attributes are stored as follows in the solution
level folder:
a) Use AssemblyVersionInfo.cs to store the assembly version only. This is appropriate if
you use a build tool to alter the assembly version during the build process.
b) Use CommonAssemblyInfo.cs to store other common assembly attributes.
In the projects that reference these attributes add a linked file to the project. Note that in
web projects this will not work. In this case you will need a pre-build event to copy the
appropriate solution level assembly information file to the project folder.

2.4 Using Directive


The using directives should appear in the following order:
a) .Net Framework Class Library namespaces

C#_Coding_Standards_CH02.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 2 - Page 1 of 2
C# Coding Standards

b) Third-party namespaces
c) Vero Common or Application Library namespaces
d) Project-specific namespaces
Use a blank between each of these groups. This setting can be set within Resharper allowing
the reformatting option to do this for you. See Standard Resharper Settings for information
on configuring your Resharper environment.

2.5 Directory Layout


The layout of directories should correspond with each part of a namespace. This means
creating a folder per namespace part except in the case of the project folder.
The following example shows the Vero Application Library.

Note the following:


a) The Vero.Common folder holds the Vero.Common project. All declarations in this folder
belong to the Vero.Common namespace.
b) The DataTransferObjects folder holds all declarations in the
Vero.Common.DataTransferObjects namespace.
c) All solution level items are placed in a folder called “SolutionItems”. This folder
contains referenced assemblies, common assembly information files, the strong key
file for the solution etc.

C#_Coding_Standards_CH02.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 2 - Page 2 of 2
C# Coding Standards

3 Layout
3.1 Objectives of Good Layout
A good layout scheme should achieve the following:
a) Accurately represent the logical structure of the code.
b) Consistently represent the logical structure of the code.
c) Improve readability.
d) Withstand modifications. That is modifying one line of code shouldn’t require modifying
several others.
Much of the layout specified in this section can be configured within Resharper so that the
code reformatting command can implement these standards automatically. See Annex A for
information on Visual Studio settings.

3.2 Braces and Parentheses


When using braces:
a) Put braces on a separate line for namespaces, classes, methods and blocks.
b) Put braces for simple property access methods (including interface declarations) on a
single line.
c) Place the opening brace of a statement on the next line of the statement, and aligned
in the same column as the first character of the statement.
d) Align opening and closing braces in the same column.
e) Use braces for single line statements.
Example:

class Sample
{
int _duration;
int _count;

public Sample( int duration, int count )


{
Duration = duration;
Count = count;
}

public int Duration


{
get { return _duration; }
set
{
if ( value > 0 )
{
_duration = value;
}

C#_Coding_Standards_CH03.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 3 - Page 1 of 7
C# Coding Standards

else
{
_duration = 0;
}
}
}

public int Count


{
get { return _count; }
set { _count = value; }
}
}

3.3 Indentation
Your indentation width and character (that is a tab or spaces) can be set using Visual Studio.
When indenting:
a) Do not use tabs for indentation. Set your tab size to 4 spaces (from this point in the
document “tab” refers to the four spaces generated by your editor when hitting the tab
key). The reasons are as follows:
i) Spaces always make the code appear the same way; whether you view the
code within Visual Studio or Notepad (Notepad has a tab size set to 8 spaces).
ii) Tabs do not align neatly under function call parameter lists. You end up
needing a combination of tabs and spaces. This leads to differences in
appearance when viewed in a different editor or on a developer environment
with a different tab size setting.
b) Do not indent namespace definitions.
c) Indent class definitions one tab from the left margin.
d) Indent methods and properties one tab from the left of the current class definition.
e) Indent region directives at the same indentation level as the encapsulated region.
Example:

namespace Vero.Sample
{
class SampleClass
{
#region Constructors

public SampleClass()
{
// Initialise something
}

C#_Coding_Standards_CH03.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 3 - Page 2 of 7
C# Coding Standards

#endregion

public int DoSomething( int a, int b )


{
int result = a + b;
return result;
}
}
}

3.4 Spaces
Apply the following when using spaces:
a) Follow a key word with a space where a conditional-expression follows the key word.
This helps to distinguish keywords from method calls.
For example:

while ( condition )
{
// do stuff
...
}

b) Separate all binary operators except “.” from their operands by a single space. Do not
use a space to separate unary operators.

c) A single space should appear directly after a comma in an argument list. There should
be no space before the comma.

d) Do not place a space before a semicolon after an expression.

e) Expressions in a for statement should be separated by a single space.

f) Casts should be followed by a space

g) Space out array references.

h) Space out expressions within parentheses


For example:

C#_Coding_Standards_CH03.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 3 - Page 3 of 7
C# Coding Standards

a += c + d;
a = ( a + b ) / ( c * d );

for ( int i; i <= 10; i++ )


{
// process loop
}

HelperMethod( “Demo spacing”, ( string ) secondArg );


arrayVar[ 1 ][ 2 ] = 10;

3.5 Line Length


Lines should be no longer than 90 characters. This is the maximum number of characters
that will print without word wrapping using 10 point Courier New font (the default Visual
Studio code font) and keeping the default left and right margins.

3.6 Line Breaks and Long Statements


When a statement is too long to fit onto a single line, apply the following guidelines:
a) Make it obvious that the part of the statement on the first line is only part of a
statement. The easiest way to do this is to make the first line syntactically incorrect if
it were just a single line.
b) Place operators and commas at the end of the continuation line.
c) Indent the subsequent lines the standard amount. That is not under the assignment
operator or the open parenthesis of a control-statement. While this approach is
visually appealing it leads to overly broken lines if you are deeply indented already. It
also makes renaming require the reformatting of multiple lines.
d) Note that when Resharper (version 1.5.1) reformats a multi-line method call it will
indent the parameters on subsequent lines with the open parenthesis. All other
continuations are indented as per the previous point. As this requires no extra
reformatting this is acceptable.
e) Keep closely related elements together.
Example of a long assignment use:

customerBill = PreviousBalance( paymentHistory [ customerID ] ) +


LateCharge( paymentHistory[ customerID ] );

Instead of:

customerBill = PreviousBalance( paymentHistory[ customerID ] ) + LateCharge


( paymentHistory[customerID ] );

Or instead of:

customerBill = PreviousBalance( paymentHistory [ customerID ] )


+ LateCharge( paymentHistory[ customerID ] );

Or instead of:

C#_Coding_Standards_CH03.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 3 - Page 4 of 7
C# Coding Standards

customerBill = PreviousBalance( paymentHistory [ customerID ] ) +


LateCharge( paymentHistory[ customerID ] );

Example of a long control-statement use:

for ( int employeeNum = empBatch.First + empBatch.Offset;


employeeNum < empBatch.First + empBatch.Offset + empBatch.Total;
employeeNum++ )
{
// loop code
}

Instead of:

for ( int employeeNum = empBatch.First + empBatch.Offset;


employeeNum < empBatch.First + empBatch.Offset + empBatch.Total;
employeeNum++ )
{
// loop code
}

3.7 Line Spacing or Grouping


A group of code is analogous to a paragraph in writing. As such groups of related code
should be separated by a single blank line.

3.8 Laying out Classes and Interfaces


The following table illustrates the order in which class declaration components should appear.
Note document comments and the comment block are discussed later in chapter 7.
Part of class / interface Notes
declaration
1 Class or interface statement Contains alphabetic characters with Pascal
casing
2 Class (static) variables List variables in the following order:
• Public
• Protected
• Internal
• Private
Note all public and protected variables must
have a XML Documentation comment.
3 Class (static) methods List methods in the following order:
• Public
• Protected
• Internal
• Private

C#_Coding_Standards_CH03.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 3 - Page 5 of 7
C# Coding Standards

4 Delegates Name a delegate as per naming a method


5 Events Name an event as per naming a method.
6 Instance variables As for 2.
Initialise an instance variable in a
constructor or a property. When in the
constructor, call a property if the instance
variable has a set property instead of
setting the variable directly.
7 Constructors Default constructors should precede
constructors with parameters.
Re-use constructors where possible instead
of duplicating code.
If a constructor is private, comment on why
it is private.
8 Properties All instance variables that can be set
externally from a class must have setter
accessors.
All variables that can be accessed externally
from a class must have getter accessors.
Prefer property access to instance variable
access even from within a class.
9 Methods As for 3

3.9 Using Regions


Regions help group logically related parts of a class by allowing the region to be collapsed
within the Visual Studio editor. They also aid developers who revisit the class to quickly
locate the area of the class they need to concentrate on. The following are some guidelines
to using regions:
a) Large classes (greater than 2000 lines) should be rare in a project, but when they are
needed use regions to divide the class as per the class part table above.
b) When implementing an interface, Visual studio prompts you to generate stub methods
to implement the interface. These stubs are surrounded by regions. These regions
should be kept and maintained accurately.
c) When overriding a parent class method or property, surround the method(s) or
property(s) with an appropriate region. Keep the methods and properties in the
appropriate section as per the above class part table.

3.10 Laying Out Comments


Apply the following guidelines when laying out comments. See Chapter 7 for a full discussion
on applying comments.
a) Indent a comment with its corresponding code. Leaving a comment left indented while
the code it describes is indented interferes with the logical structure of the code, thus
making it more difficult to read.
b) Set off each comment with at least one blank line except if the comment is the first
line below a brace. This applies to single or multi-line comments.
c) Avoid end line comments apart from variable declarations.
Example:

C#_Coding_Standards_CH03.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 3 - Page 6 of 7
C# Coding Standards

{
// Comment describing the first statement
CodeStatementZero;
CodeStatementOne;

// Comment block on statements


// two and three
CodeStatementTwo;
CodeStatementThree;
}

C#_Coding_Standards_CH03.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 3 - Page 7 of 7
C# Coding Standards

4 Naming Conventions
4.1 Capitalisation Styles
4.1.1 Pascal Casing
This convention capitalises the first character or each word (as in ClassName).
4.1.2 Camel Casing
This convention capitalises the first character of each word except the first one (as in
parameterName).
4.1.3 Upper Case
Use upper case in the following scenarios:
a) Where an identifier consists of an abbreviation which is one or two characters long.
Abbreviated identifiers with three or more characters should use Pascal Casing.
b) Any constant identifier that is not part of an enumeration or class with ONLY public
static constants should use ALL_CAPS. This helps distinguish the constant in code.
4.1.4 Capitalisation Table
Apply the guidelines in the following table when capitalising program elements
Type Case Notes
Class / Struct Pascal Casing
Interface Pascal Casing Use a prefix of “I”
Enum Values Pascal Casing
Enum Type Pascal Casing
Events Pascal Casing
Exception Pascal Casing Use a “Exception” suffix
Class
Public Fields Pascal Casing Should only exist in data only classes or
Structs.
Methods Pascal Casing
Namespace Pascal Casing
Property Pascal Casing
Protected Camel Casing Reference within methods using “this.”
Fields
Private Fields Camel Casing Use a prefix of “_”
Parameters Camel Casing

4.2 Naming Guidelines


Generally the use of underscore characters inside names (with the exception of those
described in section 4.1.3) and naming according to the guidelines for Hungarian notation
are considered bad practice.
Hungarian notation is a defined set of pre and postfixes which are applied to names to reflect
the type of the variable. This style of naming was widely used in early Windows
programming, but now is obsolete or at least should be considered deprecated. Using
Hungarian notation is not allowed in Vero project code.
A good variable name describes the semantic not the type. Do not use single letter variable
names (except in simple loops) or variable names such as “temp” or “max”.
An exception to this rule is GUI code. All fields and variable names that contain GUI elements
like button should be suffixed with their type name without abbreviations.

C#_Coding_Standards_CH04.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 4 - Page 1 of 4
C# Coding Standards

For example:

System.Windows.Forms.Button _cancelButton;
System.Windows.Forms.TextBox _nameTextBox;

4.2.2 Names to Avoid


Avoid the following names
a) Misleading names or abbreviations
b) Avoid names with similar meanings within the same piece of code
c) Avoid variables with different meanings but similar names
d) Avoid numerals in names
e) Avoid misspelled words in names
f) Don’t differentiate names solely by capitalisation
4.2.3 When using Abbreviations
Apply the following guidelines for abbreviations if they must be used:
a) Do not use abbreviations if they are open to interpretation. If you are unsure deciding
between an abbreviated name and a full name, always go with the full name.
b) Don’t abbreviate by removing a single character
c) Abbreviate consistently. For example, don’t use Num on one part of the program and
No in another.
d) If abbreviations are part of the business they should be documented at the project
level in a standard abbreviations section of the requirements document.
e) Use Pascal casing for abbreviations of 3 characters or more, otherwise use all
uppercase characters.

4.2.4 Class / Struct Naming Guidelines


a) Class names must be nouns or noun phrases.
b) Use Pascal Casing
c) Do not use any class prefix
d) Exception classes should be suffixed with “Exception”
4.2.5 Interface Naming Guidelines
a) Name interfaces with nouns or noun phrases or adjectives describing behaviour.
(Example IComponent or IEnumerable)
b) Use Pascal Casing
c) Use I as the prefix for the name, it is followed by a capital letter (first char of the
interface name)
4.2.6 Enum Naming Guidelines
a) Use Pascal Casing for enum value names and enum type names
b) Don’t prefix (or suffix) a enum type or enum values
c) Use singular names for enums
d) Use plural name for bit fields.
4.2.7 ReadOnly and Const Field Names
a) Name static fields with nouns, noun phrases or abbreviations for nouns
b) Use underscore separated ALL_CAPS words.
c) Use Pascal casing if the entire class or struct contains static constants.

C#_Coding_Standards_CH04.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 4 - Page 2 of 4
C# Coding Standards

4.2.8 Parameter Names


a) Use descriptive names, which should be enough to determine the variable meaning
and its type. But prefer a name that’s based on the parameter’s meaning.
b) Use Camel Casing
4.2.9 Variable Names
a) Counting variables are preferably called i, j, k, l, m, n when used in 'trivial' counting
loops. See 4.2.14 for an example on more intelligent naming for global counters etc.
b) Use Camel Casing
4.2.10 Field Names
a) Use descriptive names, which should be enough to determine the variable meaning
and its type.
b) Use Camel Casing with a “_” prefix.
4.2.11 Method Names
a) Methods should be named with verbs or verb phrases. If you are struggling to find a
concise name for the method, chances are it is doing more than one thing and should
be broken into more methods.
b) Use Pascal Casing
4.2.12 Property Names
a) Name properties using nouns or noun phrases
b) Use Pascal Casing
c) Consider naming a property with the same name as the instance variable it
encapsulates (of course no “_” and Pascal casing instead of camel casing).
4.2.13 Event Names
a) Name event handlers with the EventHandler suffix
b) Use two parameters named sender and e
c) Use Pascal Casing
d) Name event argument classes with the EventArgs suffix
e) Name event names that have a concept of pre and post using the present and past
tense
f) Consider naming events using a verb.
4.2.14 Variable Naming Example (from ICSharp Style guide)
Instead of:

for ( int i = 1; i < num; ++i )


{
meetsCriteria[ i ] = true;
}

for ( int i = 2; i < num / 2; ++i )


{
int j = i + i;
while ( j <= num )
{
meetsCriteria[ j ] = false;

C#_Coding_Standards_CH04.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 4 - Page 3 of 4
C# Coding Standards

j += i;
}
}

for ( int i = 0; i < num; ++i )


{
if ( meetsCriteria[ i ] )
{
Console.WriteLine( i + " meets criteria" );
}
}

Try intelligent naming:

for ( int primeCandidate = 1; primeCandidate < num; ++primeCandidate )


{
isPrime[ primeCandidate ] = true;
}

for ( int factor = 2; factor < num / 2; ++factor )


{
int factorableNumber = factor + factor;
while ( factorableNumber <= num )
{
isPrime[ factorableNumber ] = false;
factorableNumber += factor;
}
}

for ( int primeCandidate = 0; primeCandidate < num; ++primeCandidate )


{
if ( isPrime[ primeCandidate ] )
{
Console.WriteLine( primeCandidate + " is prime." );
}
}

Indexer variables should generally be called i, j, k etc. But in cases like this, it may make
sense to reconsider this rule. In general when the same counters or indexers are reused,
give them meaningful names.

C#_Coding_Standards_CH04.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 4 - Page 4 of 4
C# Coding Standards

5 Declarations
5.1 Number per Line
Use only one declaration per line for the following reasons:
a) It’s easier to put a comment next to each declaration. Note a better variable name is
preferable to a variable that requires an explanatory comment.
b) It’s easier to modify declarations because each declaration is self contained.
c) It’s easier to find variables because it’s easier to scan a column than it is to scan a
line.
d) It’s easier to find and fix syntax errors because the line number the compiler gives you
has only one declaration on it.

5.2 Initialisation
Initialise all local variables where they are declared.
Initialise class instance fields in constructor code. If the instance field has a public setter
property, use the property’s set method to initialise the value. This guarantees only a single
point where that instance field is altered.
If you are initialising any object that implements System.IDisposable, try the using
statement:

using ( OpenFileDialog openFileDialog = new OpenFileDialog() )


{
...
}
As with any other declaration, put each new declaration in the scope of the using statement
on a new line. Also indent the standard amount:

using ( StreamWriter sortedFile = new StreamWriter( "Sorted.txt" ),


errorFile = new StreamWriter( "Errors.txt" ) )
{
...
}

5.3 Placement
Declare each variable as close as possible to where it’s first used for the following reasons:
a) This reduces the “average span” of a variable. Span is the number of lines between
references to a variable. Average span is the average of all such references. By
reducing average span you enable the reader of your code to focus on a single section
of the code at a time. You also reduce the window of vulnerability. That is the
opportunity for subsequent developers to inadvertently change the variable to an
unexpected value.
b) It also reduces the “live time” of a variable. Live time is similar to span except the
number is calculated as the number of lines between the first reference and the last
reference regardless of the number of times it is used in between. Reduced live time
reduces the window of vulnerability; it also allows a developer to show all references
to a variable on the screen at the same time making the code more readable. See ref
MCCONNELL04 Section 10.4 for more detail this and the previous point.
c) This facilitates refactoring code into smaller routines when necessary. This is achieved
in Resharper by highlighting the code and selecting Refactor | Extract Method from

C#_Coding_Standards_CH05.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 5 - Page 1 of 2
C# Coding Standards

the shortcut menu. If the variables where declared in a block at the top of the method
this would not be done easily.
Avoid local declarations that hide declarations at a higher level.
Example:

int count;
...
MyMethod()
{
if ( condition )
{
int count = 0; // Avoid!
...
}
...
}

5.4 Attributes
Align an attribute with the type or member it applies to. Place the attribute above in all
cases. For example:

[ Category( "Vero GUI Lib" ),


Description( "Sets the security Function Id for the control" ),
DefaultValue( "" ),
Bindable( true ) ]
public string SecurityContext
{
...
}
Note the standard (as defined at VAL Standard Resharper Settings) Resharper settings will
change the above to the following:

[ Category( "Vero GUI Lib" ) ]


[ Description( "Sets the security Function Id for the control" ) ]
[ DefaultValue( "" ) ]
[ Bindable( true ) ]
public string SecurityContext
{
...
}

C#_Coding_Standards_CH05.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 5 - Page 2 of 2
C# Coding Standards

6 Statements
6.1 Simple Statements
Each line should contain at most one statement, for example:

lineCount++; // Correct
pageCount++; // Correct
lineCount++; pageCount++; // Avoid!!

6.2 Return Statements


A return statement should not use parentheses unless they make the return value more
obvious in some way.
Example:

return;
return myDisk.Size();
return ( ( size > 0 ) ? size : DEFAULT_SIZE );

Use only one return statement at the end of the method if possible. Otherwise clearly
identify the other return statement with comments.

Example:

If ( param == null )
{
// EARLY RETURN – bad parameters
return null;
}

Do not use a return statement in a try / catch or finally block.

6.3 Break Statements


break statements should generally be limited to switch statements. Add comments if you
use them in other statements.
Example:

for ( int i = 0; i < 50; i++ )


{
if ( i == j )
{
// Found it, no need to continue
break;
}
}

6.4 If, if-else, if else-if Statements


The if-else statement should have the following form. ALWAYS put braces around single
statements (Resharper will do this for you when you reformat code).

C#_Coding_Standards_CH06.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 6 - Page 1 of 5
C# Coding Standards

if ( condition )
{
StatementOrStatements;
}

if ( condition )
{
StatementOrStatements;
}
else
{
StatementOrStatements;
}

if ( condition )
{
StatementOrStatements;
}
else if
{
StatementOrStatements;
}
else
{
StatementOrStatements;
}

Generally, in conditional expressions, put constants on the right side of the relation. Putting
them on the left was a handy standard for C and C++ standards because the languages
allowed you to make an assignment within a conditional expression (this always evaluates as
true). Since C# does not allow this, the more naturally readable standard now applies.
Example:

// Use this form


if ( i < 10 )
{
...

// Avoid this form


if ( 10 >= i )
{
...

C#_Coding_Standards_CH06.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 6 - Page 2 of 5
C# Coding Standards

6.5 For/Foreach Statements


ALWAYS put braces around single statements (Resharper will do this for you when you
reformat code). When looping through collections that implement IEnumerable, prefer
foreach over for loops.
Add a comment if you use a continue statement.
The for/foreach statements should be written as follows:

// for statement
for ( initialisation; condition; update )
{
StatementOrStatements;
}

// foreach statement
foreach ( int k in MyList )
{
StatementOrStatements;
}

6.6 While/do-while Statements


A while statement should be written as follows:

while ( condition )
{
StatementOrStatements;
}

An empty while should be written as follows:

while ( condition )
{
}

A do-while should be written as follows:

do
{
StatementOrStatements;
} while ( condition );

Add a comment if you use a continue statement.

6.7 Switch Statements


A switch statement should be written as follows:

C#_Coding_Standards_CH06.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 6 - Page 3 of 5
C# Coding Standards

switch ( condition )
{
case A:
statements;
break;
case B:
statements;
break;
default:
statements;
break;
}

Include a default case in every switch statement.

6.8 Try-catch statements


A try-catch statement should be written as follows:

// Simple try-catch
try
{
StatementOrStatements;
}
catch ( ExceptionClass e ) // Only declare e if it is used!
{
StatementOrStatements;
}

// Try-catch-finally
try
{
StatementOrStatements;
}
catch ( ExceptionClass e ) // Only declare e if it is used!
{
StatementOrStatements;
}
finally
{
StatementOrStatements;
}

C#_Coding_Standards_CH06.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 6 - Page 4 of 5
C# Coding Standards

6.9 Properties and Indexers


Properties and Indexers should be written as follows:

// Interface or abstract type declaration


interface I
{
int Property { get; set; }
}

// Simple Property declaration


class C
{
private int Property
{
get { return x; }
set { x = value; }
}
}

// Simple Access Method


class C
{
private int Property
{
set { x = value; }
get
{
if ( condition )
{
return x;
}
}
}
}

C#_Coding_Standards_CH06.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 6 - Page 5 of 5
C# Coding Standards

7 Comments
Comments come in a number of different forms as outlined in the following sections.

7.2 Implementation Comments


Implementation comments are delimited by /*... */, or //. They are used to comment out
blocks of code or to describe pieces of code within classes.
Apply the general guidelines in the following sections to any implementation comments.
7.2.2 Do not repeat what the code does
It gives the reader of the code more to read without adding any value.
7.2.3 Justify violations of good coding practice
Code that is complicated or tricky should be reconsidered before writing comments to explain
what is going on. If performance has been identified as a problem in the code and is
therefore the reason for the complicated code, include the reason AND the results from your
tests. If you haven’t tested your more efficient code and don’t have time to, use code that is
easier to read.
7.2.4 Comment previous complicated code that can’t be changed
If you come across complicated or tricky code and don’t have the latitude to change it, then
by all means add a comment.
7.2.5 Explain the why rather than the what
When commenting on a paragraph of code, explain the intent of code or the why rather than
the what. This is particularly useful if you are writing business logic. If something looks odd,
explain the business decision or site the specification reference.
7.2.6 Keep the comment consistent with the level of abstraction of the class
For example if you are populating a hash table of member addresses in a business object,
don’t put the comment “Call usp_GetAddressesByMmemberId then populate hash table”.
Instead use a comment such as “Retrieve current addresses for a member”
7.2.7 Write English comments
I.e. don’t omit capitalisation or punctuation. Use complete sentences where appropriate and
avoid abbreviations.
7.2.8 Do not leave blocks of commented code behind
Never submit code with blocks of code commented out for review. Never check code into the
main branch (trunk in Subversion) with blocks commented out.
7.2.9 Do not use “pretty comments”
Never create boxes or other borders using comments as these are hard to maintain.
7.2.10 The pseudocode technique
If you use the Pseudocode programming technique outlined in Chapter 9 of Code Complete
(see ref MCCONNELL04), leave these comments behind.
7.2.11 Maintenance notes
Do not use comments to document maintenance notes. This should be done during the check
in process. Differences can also be seen using your source control tool.
7.2.12 Changes to code
If you make a change to the code that makes the comment inaccurate or irrelevant, update
the comment as well.
7.2.13 Summary Comments
Confine method and property summary comments to document comments.
7.2.14 Marker comments
Only use the special marker comments defined in Visual Studio. See section 7.4 below.

C#_Coding_Standards_CH07.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 7 - Page 1 of 5
C# Coding Standards

7.2.15 Low level design explanations


Explain low level design issues in the Header comment.

7.3 Documentation Comments


Documentation comments are mandatory in all Vero C# projects. They are used to document
what a class and its components do and how to use them. The goal of documentation
comments and the reason they are mandatory is to produce MSDN style documentation
using the NDoc tool (http://ndoc.sourceforge.net/). This is particularly important when
developing library code.
The document comments you use to describe a class or one of its components should be
meaningful enough for a reader of the help file to be able to use your class without having to
look at the source code, just as you use .Net framework documentation without wishing you
had access to its code.
Apply the following guidelines when using documentation comments:
a) Full documentation comments are mandatory for all public and protected declarations.
At a minimum this means supplying:
i) A <summary> tag
ii) A <param> tag for each method parameter
iii) A <returns> tag for each method that has a return value
iv) An <exception> tag for any methods or properties that throw any exceptions
b) Use summary documentation comments for all private and internal declarations. I.e.
the <summary> tag is the only required tag.
c) Keep <summary> tags brief. The contents of these tags appear in the IntelliSense
popup menus.
d) When a declaration requires a more detailed description use the <remarks> tag.
Separate paragraphs using the <para> tags. Use the <list type> tag to show bullet
points.
e) Use the <cref> or <href> tags for cross references, so a link is generated in the
resulting help file or pages.
f) Use the <example> and <code> tags if you feel an example will add value to the
generated help file.
The following example shows a documentation comment (reformatted here to fit within the
page) in the Microsoft Enterprise library and a screen shot of its corresponding help page:

/// <summary>
/// <para>
/// Adds a new instance of an <see cref="DB2Parameter"/> object
/// to the command set as <see cref="ParameterDirection"/> value of
/// Input.
/// </para>
/// </summary>
/// <param name="name">
/// <para>The name of the parameter.</para>
/// </param>
/// <param name="dbType">
/// <para>One of the <see cref="DbType"/> values.</para>
/// </param>
/// <remarks>
C#_Coding_Standards_CH07.doc CONFIDENTIAL Version 0.1 (DRAFT)
Standards and Procedures Chapter 7 - Page 2 of 5
C# Coding Standards

/// <para>
/// This version of the method is used when you can have the same parameter
/// object multiple times with different values.
/// </para>
/// </remarks>
public override void AddInParameter( string name, DbType dbType )
{
...

And the help page:

For more information on XML Documentation see the following links:

• XML Documentation Tutorial

• XML Documentation Reference

• http://ndoc.sourceforge.net/

7.4 Special Comments


Special Comments are user defined tag values that allow Visual Studio to place the content
of the comment in the Task List after performing a build.
Example:

// TODO Implement action method

C#_Coding_Standards_CH07.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 7 - Page 3 of 5
C# Coding Standards

The tags can be set using the Tools | Options menu and selecting Environment | Task
List:

The tokens in the screen shot are self explanatory. If adding new tokens they must be
agreed upon by the entire project, so the build results in the same Task List entries for all
developers.
Comment token tasks are not shown by default in the Task List after a build. To enable task
list generation, right click in the task list and select Show Tasks | All.

7.5 Header Comment


The header comment must appear at the top of every C# source file no matter how trivially
small. The format is as follows:

/*****************************************************************************************
*
* Description : <Declaration Description>
*
*
* Configuration Record
*
* Review Version Author Date Chg No.
* 000 1.0 <Developer name> <Date> <Change No>
*
*****************************************************************************************
*
* History
*
* Version Description
* 1.0 Original
*
****************************************************************************************/

The components are as follows:

C#_Coding_Standards_CH07.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 7 - Page 4 of 5
C# Coding Standards

a) Description is a brief description of the object. If there are any low level design issues
to mention here is the place to do it.
b) The review number should be assigned to you when you work on a piece of work. This
is usually done by maintaining an index document. See your project lead for
information on how this is done on your project.
c) The version number is incremented arbitrarily here. I.e. it does not relate to the
version of the resultant assembly or revision number in your source control tool. It is
incremented prior to submitting your code for review.
d) The author name should be your full name. Not your LAN user id or your nick name.
e) Change number is only required when you make a change beyond the originally
specified requirement. When coding the original version the change number is
“Original”. It is assigned to you using what ever mechanism your project has in place.
This can either be a change number from a Notes database or a Ticket number from
Trac. See your project lead for information on how this is done on your project.
f) The history section is used to fit a meaningful description of why the code was
changed. The version number in this section should link with the version number you
created in the Configuration Record section. This prevents tiny descriptions from being
included in a configuration record or descriptions that run over a few lines in a small
column.

C#_Coding_Standards_CH07.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 7 - Page 5 of 5
C# Coding Standards

8 Programming Practices
8.1 Visibility
Do not make any instance or class variables public. Make them private and use Properties to
access the data. Resharper will allow you to generate Properties from instance variables
automatically so there is little overhead in having to create the Properties.
The only exception is the data string constant class that contains only static members.
Example:

public class PolicyStatus


{
public static const string Current = "CU";
public static const string PendingPayment = "PP";
public static const string Inactive = "IA";

// Do not allow instantiation only allow static field access


private PolicyStatus()
{
}
}

A full discussion of Class visibility can be found in Chapter 5 of Code Complete.

8.2 No “Magic” Variables


8.2.1 Magic Numbers
Magic numbers are the harded code numeric literals that appear in your code without
explanation. Avoiding magic numbers yields the following advantages:
a) Changes can be made more reliably. For example the number 100 can represent a
maximum number of entries or appear in a percentage validation. If a maximum
number of entries changes, you could either miss one or change the percentage range
inadvertently.
b) Changes can be made more easily. It’s obviously easier to change a single named
constant than every occurrence of a literal.
c) Code is more readable. Most developers understand that a literal representing say
max entries is a bad choice and use a named constant in its place. But then go on to
use a hard coded 1000 to convert from one unit to another.
Example:

C#_Coding_Standards_CH08.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 8 - Page 1 of 6
C# Coding Standards

// Are we adjusting the value here or doing a unit conversion?


// If you aren’t familiar with the System.Timer class you would need to look
// in MSDN Docs to be sure.
myTimer.Interval = recurringInterval * 1000;

// Use the constant


private const int SECONDS_TO_MILLISECONDS = 1000;
...
// It is now clear even at a glance this is a unit of time conversion
myTimer.Interval = recurringInterval * SECONDS_TO_MILLISECONDS;

8.2.2 Magic Characters and Strings


In the same vein as magic numbers, these are literal strings and characters, but seem less
innocuous and are therefore more common. The following are some things to consider:
a) For common names in a program like the program name, menu display text, a report
title or a version number string. Do the following:
i) Use a resource file, the database or named constants for programmatic names
such as menu items, report titles etc.
ii) Use reflection to get a version number or the application name. All Vero
projects have a versioning mechanism in the overnight build and release
processes. Open up an AssemblyInfo.cs file for all the options you have at your
disposal.
b) For any messages that make their way to the presentation tier never use a hard
coded string literal. Always use either a resource file or a database. The system design
specification should explicitly provide direction on this. If localisation is a possibility in
the project, plan for it upfront rather than attempting a retrofit late in delivery. It is
acceptable to instantiate exception objects with a literal supplied for the message as
long as this message is never bubbled to the presentation tier.
c) For special characters apply the following guidelines:
i) Use Environment.NewLine instead of ‘\n’.
ii) Use inputChar.IsDigit or inputChar.IsLetter etc rather than if (inputChar >= ‘0’
|| inputChar <= ‘9’) etc. The Char struct has just about any alpha-numeric /
punctuation check you can think of.
iii) Use String.Empty instead of “”.
iv) For situations not explicitly offered by the .Net Framework use a named
constant or variable rather then hard-coding the character code.

8.3 Refactoring
Martin Fowler defines Refactoring as “a change made to the internal structure of the software
to make it easier to understand and cheaper to modify without changing its observable
behaviour” (FOWLER99). The idea stems from the reality that software development does
not flow from static requirements that are never altered until after implementation. It’s
about being able to cope with the reality that changes are inevitable and that better solutions
present themselves during successive changes to units of work. Refactoring offers a formal
repeatable method one can use to improve the quality of code.
The purpose of this section is to make you aware of the resources available both as learning
aids and as tools.
8.3.2 Learning
The following are the written resources we have available in the Systems and Projects
Library:

C#_Coding_Standards_CH08.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 8 - Page 2 of 6
C# Coding Standards

a) Martin Fowler’s Refactoring book. This book describes Refactoring by example and has
a catalogue of refactorings. The first sections walk you through a small sample
program and how refactoring can improve the program’s quality. The later sections are
the refactorings catalogue.
b) http://www.refactoring.com/. This web site offers up to date information on
Refactoring, including more refactorings and links to tools that automate the process.
c) Chapter 24 of Code Complete. This offers a concise introduction to Refactoring. If you
don’t read Martin Fowler’s book, I urge you to at least read this section.
d) http://www.martinfowler.com/. This web site offers more information on Refactoring
as well as patterns, agile development techniques etc.
8.3.3 Tools
Many of the refactorings outlined in the texts above can be performed automatically using
Resharper. See the Resharper Refactoring Help Index for a complete list of the refactorings
offered by this tool.
Visual Studio.Net 2005 also offers automated Refactoring.

8.4 Unit Testing


One of the cornerstones of refactoring is the ability to prove that changes made have not
broken the code. This is done by using automated unit testing. I.e. writing a test application
to automatically exercise the code you have written.
The Vero standard unit test tool for this purpose in NUnit. In order to use NUnit effectively,
you need to consider the following:
a) Never place unit testable logic in an executable. NUnit can only load library assemblies
– i.e. dlls. Testing GUI code can be automated using NUnit ASP or NUnit Forms. Again,
if you want to use these tools see the documentation before you start code to ensure
your code is testable by these tools.
b) Test your logic close to where it runs. For example if you are testing an application
that uses a remoting interface have your unit tests invoke the logic in the same tier
rather than having to initialise a remoting pipeline every time.
c) Never have a public method rely on a resource that is not made obvious by the
interface. For example, opening a hard coded file within the method is poor. Pass the
file name as a parameter.
d) If you need to use a class that works with external resources to your program in order
to perform a unit test, consider creating an interface for your external resource class
and working with a stub version of that class for the purpose of exercising your tests.
This is commonly referred to as a “mock” object. By doing this you gain the following
advantages:
i) External resources such as databases can be slow to work with making the
testing process slow. Using a mock object that simulates database access can
speed up your unit tests.
ii) External resources tend to have difficult to reproduce or random errors that
must be tested for. For example you may need to cater for a database timeout
to test some retry logic or you may need to test for a networking error in a
remoting application. You can create a mock object that simulates these
difficult to create scenarios.
8.4.2 More information
The following are where you can find more information on unit testing
a) See http://www.nunit.org/ for the NUnit home page.
b) Other testing frameworks are:
i) http://nunitasp.sourceforge.net/
ii) http://nunitforms.sourceforge.net/

C#_Coding_Standards_CH08.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 8 - Page 3 of 6
C# Coding Standards

c) See Test-Driven Development by David Astels (Vero Systems & Projects Library) for a
full discussion on unit testing and Chapter 7 for an example of using Mock Objects.
Also see http://www.mockobjects.com/FrontPage.html for information on the web.

8.5 Level of Abstraction


The idea behind abstraction is to be able to engage with a concept while safely being able to
ignore some of the detail - to handle different details at different levels.
For example when you consider a car and how to drive it, you think of putting the car into
gear, steering, using the accelerator and so on. You don’t think about the process of how the
internal combustion engine converts fuel into power to the wheels or how the suspension
system makes the ride smoother. If you were required to say initialise the car’s subsystems
and actively monitor them while you were driving there would either be fewer drivers or
more accidents.
This concept can be extended to writing classes. That is the level of abstraction should be
consistent within the class. For example a high level business object should not be dealing
with low level data structures like hash tables or array lists.
A more specific example is as follows (MCCONNELL04)

// Class interface that presents a poor abstraction (method stubbs only)


public class Program
{
public void InitialiseCommandStack()

public void PushCommand( Command command )

public Command PopCommand()

public void ShutdownCommandStack()

public void InitialiseReportFormatting()

public void FormatReport( Report report )

public void PrintReport( Report report )

public void InitialiseSingletons()

public void DisposeSingletons()


}
Better abstraction:

\\ Low level data structure setup moved to different classes


\\ High level methods like printing specific reports moved to different classes
public class Program
{
public void InitialiseUserInterface()

C#_Coding_Standards_CH08.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 8 - Page 4 of 6
C# Coding Standards

public void ShutDownUserInterface()

public void InitialiseReports()

public void ShutdownReports()


}

More information on this subject can be found in Chapter 6 of Code Complete.

8.6 Defensive Programming


Defensive programming refers to the practice of protecting your routines from unexpected
events or from the mistakes of other programmers. The following sections outline a starting
point for your reference. See the Defensive programming chapter of Code Complete (Chapter
8) for a more indepth discussion.
8.6.2 Garbage In
The idea of “Garbage in Garbage out” may be apparent when coding but this should never
make its way to the user. Instead use “garbage in, error out” or “no garbage in at all” (eg
key stroke filters). The key here is to always check data from external sources to your
program, be it from the user, a file, the network or any external interface.
8.6.3 Assertions
Assertions are a debugging aid. They help document the contract a method has with the
outside world. Apply the following guidelines when using assertions:
a) If you are assuming something in your code, back it up with an assertion.
b) Never remove the Debug.Assert calls from your code for production releases. The .Net
compiler removes this code for release builds.
c) Do not use Asserts for validation – again because the code is removed for release
builds.
Example:

/// <summary>
/// Returns a risk ratio based on supplied risk factors
/// </summary>
/// <param name="age">
/// Valid Insured age. Must be between 14 and 65
/// </param>
/// <param name="gender">
/// Gender to calculate ratio for
/// </param>
/// <param name="isSmoker">
/// The smoker status
/// </param>
/// <returns>
/// Returns the Risk ratio expressed as a decimal between 0 and 1
/// </returns>

C#_Coding_Standards_CH08.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 8 - Page 5 of 6
C# Coding Standards

public decimal GetRiskRatio( int age, Gender gender, bool isSmoker )


{
Debug.Assert( ( age >= 14 && age <= 65 ),
" Age should be between 14 and 65" );

decimal riskFactor = 10M;

// Do method work

// Assert the factor falls into range


Debug.Assert( ( riskFactor >= 0M && riskFactor <= 1M ),
"Error calculating risk factor" );
return riskFactor;
}
If the assertion is violated a dialogue similar to the following appears. Note you are given the
context of the error so there is no need to include the method name etc in your message.

8.6.4 Exceptions
Standard exception handling practices are documented in the design standards documents.
See http://vsp/trac/val/wiki/ApplicationDesignStandards for the most current document
addressing design standards.

8.7 Use a variable for one purpose


Never define a variable used for more than one purpose. This has a few subtle follow on
implications:
a) Even temp variables can have a meaningful name. If you are thinking about your
variable names you won’t be tempted to use “tempVar” in multiple places, because
you’ll have come up with a more meaning full name for each variable.
b) Avoid variables with hidden meaning. For example you may have a variable called
pageCount that holds the number of pages printed unless it is -1, in which case
indicates an error has occurred.
c) Make sure all declared variables are used. This is the opposite of multiple uses but
is still important to avoid. The .Net compiler will warn you about this and Reshaper will
alter the colour of the variable. Never submit code that contains unused variables.

C#_Coding_Standards_CH08.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Chapter 8 - Page 6 of 6
C# Coding Standards

A Developer Environment Settings


The standard development environment for C# development consists of the following:
a) Visual Studio.Net 2003.
b) SQL Server Developer edition
c) DB2/UDB Application Development Client (version 8.2)
d) Internet Information Services
e) Jetbrains Resharper version 1.5.1

A.2 Visual Studio Settings


The only required setting in Visual Studio.Net is to have your tabs set to 4 spaces and to use
the space character. How you get the editor to indent (smart or block) is a matter of
personal preference.

A.3 Resharper Settings


There is no requirement to use Resharper to format your code, although you are required to
format your code as per this document. See Standard Resharper Settings for information on
configuring your Resharper environment to format your code to match the Vero C#
formatting requirements.

C#_Coding_StandardsAnnex_A.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Annex A - Page 1 of 1
C# Coding Standards

B Standard Code Review Checklist


This Annex provides a standard list of items that can be used during the code review
process. Each project should have a supplementary list of items that address issues that are
specific to the project.

B.2 Formatting
a) Are there any tab characters in the code?
b) Has the Resharper Reformat been applied?
c) Have regions been applied appropriately?

B.3 File Organisation


a) Is there one declaration per file?
b) Do namespaces match folder structure?

B.4 Naming Conventions


a) Have basic naming conventions been followed (chapter 4)?

B.5 Variables
a) Do variable names convey intent? I.e. does the name make the variable’s purpose
obvious?
b) Are all declared variables being used?
c) Are all declared variables being used for a single purpose?
d) Are variables declared close to first use?
e) Are there any “magic” variables (Section 8.1)?
f) Does Resharper display any warnings relating to variables?

B.6 Methods
a) Do method names convey intent? I.e. does the name make the method’s purpose
obvious?
b) Is the method name repeating parameter information? Eg GetPolicyByPolicyID(int
policyID) instead of GetPolicy(int policyID).
c) Is the method consistent with the class’s level of abstraction (section 8.5)?
d) Does the method perform a single task? How large is it? Should it be broken up?
e) Is the method assuming anything? If so are there any Asserts being used? See section
8.6.
f) Are all private methods being used (Resharper will warn on this)?

B.7 Classes
a) Is the class focusing on a single responsibility; or at least a very small number?
b) Is the class’s public interface presenting a consistent abstraction?
c) Are there any publicly visible fields (excluding constant classes)?
d) Do all public methods need to be public?

B.8 Expressions
a) Have complex Boolean expressions been extracted to either a variable or a method?

B.9 Exceptions
a) Is System.Exception being caught anywhere other than the thread level event
handler?

C#_Coding_StandardsAnnex_B.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Annex B - Page 1 of 2
C# Coding Standards

b) Does the application have a thread level handler?


c) Are any exceptions being swallowed inappropriately?
d) Are exceptions being thrown appropriately? See Application Design Standards for
appropriate exception handling.

B.10 Comments
a) Do comments accurately reflect the code? Eg has code changed to make a comment
incorrect or irrelevant?
b) Are any comments repeating what the code does?
c) Do comments explaining performance gain quote the test results?
d) Are there any blocks of commented code?
e) Are there any maintenance note comments?
f) Are all XML comments present and accurate? See section 7.3. The compiler will warn
of these. Only exceptions are generated classes such as web service proxies or Crystal
Report generated classes.
g) Are there any outstanding “TODO” comments that should have been implemented?

B.11 General
a) Are there any compiler warnings?
b) Do event handlers have any logic unrelated to the event – eg business logic?
c) Have event handler arguments been converted to appropriate objects before use?

C#_Coding_StandardsAnnex_B.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Annex B - Page 2 of 2
C# Coding Standards

C Change History
Version Date Change Description Author
0.1 29/06/2005 Original draft Christian Maslen

C#_Coding_StandardsAnnex_C.doc CONFIDENTIAL Version 0.1 (DRAFT)


Standards and Procedures Annex C - Page 1 of 1

You might also like