You are on page 1of 46

C, C++ Coding Guidelines

Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

Table of Contents
1. Purpose.............................................................................................. 5
2. Scope ................................................................................................. 5
3. Definitions And Acronyms .................................................................. 5
4. Guidelines .......................................................................................... 5
4.1. Coding Guidelines 5
4.1.1. Introduction .......................................................................................... 5
4.1.2. Indentation ........................................................................................... 6
4.1.3. Functions .............................................................................................. 6
4.1.4. Use of Spaces........................................................................................ 7
4.1.5. Variable Declaration ............................................................................... 8
4.1.6. Class Declaration ................................................................................... 8
4.1.7. Expressions ......................................................................................... 10
4.1.8. The Loop statements ............................................................................ 10
4.1.9. Use of goto,continue,break .................................................................... 11
4.1.10. The switch statement............................................................................ 12
4.1.11. The return statement.......................................................................... 13
4.1.12. Initialize all Variables ............................................................................ 13
4.1.13. Init Idiom for Initializing Objects ............................................................ 13
4.1.14. A Line Should Not Exceed 78 Characters.................................................. 15
4.2. Naming Conventions 15
4.2.1. Naming Macros .................................................................................... 15
4.2.2. Naming of Classes ................................................................................ 16
4.2.3. Variable Naming .................................................................................. 16
4.2.4. Hungarian Notation Prefixes................................................................... 17
4.2.5. Naming Methods .................................................................................. 18
4.2.6. Naming Structures and Type Definitions .................................................. 18
4.2.7. Global Constants .................................................................................. 19
4.2.8. Global Variables ................................................................................... 19
4.2.9. Reference Variables and Functions Returning References ........................... 19
4.2.10. Pointer Variables .................................................................................. 20
4.3. Documentation 20
4.3.1. Comments .......................................................................................... 20
4.3.2. Readability of Comments....................................................................... 21
4.3.3. Comments for a Block........................................................................... 21
4.3.4. Inline Comments.................................................................................. 21
4.3.5. Header for an implementation file........................................................... 22
4.3.6. Function Header in the Interface File ....................................................... 22
4.3.7. Function Header in the Implementation File ............................................. 22
4.3.8. Function Documentation in the Documentation File ................................... 23
4.3.9. Preprocessor Directives ......................................................................... 24
4.3.10. Directory Documentation....................................................................... 24
4.4. Program structure 24
4.4.1. Size of Files........................................................................................ 24
4.4.2. Size of Functions ............................................................................... 25
4.4.3. Format of an ASCII Documentation File .................................................. 26
4.4.4. Extern Declarations ............................................................................. 28
4.4.5. Multiple Levels of Control Structures ....................................................... 28
4.4.6. Static and Extern ................................................................................. 28
4.4.7. Error Handling, Dates and Reports .......................................................... 28
4.4.8. Naming Class Files ............................................................................... 28

ADITI/QMS/STDC++/1.0 Page 2 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

4.4.9. Class Definition in One File .................................................................... 28


4.4.10. Implementation in One File.................................................................... 28
4.5. Programming Construct 29
4.5.1. Goto Statements ................................................................................. 29
4.5.2. Continue and Break ............................................................................ 29
4.5.3. Return and Exit.................................................................................. 29
4.5.4. Void Functions .................................................................................... 29
4.5.5. Malloc Family of Functions .................................................................. 29
4.5.6. I / O Functions................................................................................... 29
4.5.7. Boolean Type....................................................................................... 29
4.5.8. Floating Point Constants........................................................................ 29
4.5.9. #define for Expressions....................................................................... 29
4.5.10. switch Statements............................................................................... 30
4.5.11. Required Methods for a Class ................................................................. 30
4.5.12. Justification ......................................................................................... 31
4.5.13. Use the Same Form in Corresponding Calls to new and delete..................... 31
4.5.14. Don't Over Use Operators...................................................................... 32
4.5.15. Open/Closed Principle ........................................................................... 32
4.5.16. Use of Namespaces .............................................................................. 32
4.6. Data Usage 33
4.6.1. Employ Narrowest Possible Scope ........................................................... 33
4.6.2. Do Not Define Data Types with #define ................................................... 35
4.6.3. Simulate Scope for Macros .................................................................... 36
4.7. Programming Style 36
4.7.1. Do Not Redefine Standard Items ............................................................ 36
4.7.2. Do Not Alter the Language..................................................................... 36
4.7.3. Use Straightforward Coding Style ........................................................... 37
4.7.4. Explicitly Code Boolean Expressions ........................................................ 37
4.7.5. Observe Operator Precedence Rules........................................................ 38
4.7.6. Operator Precedence Table .................................................................... 38
4.7.7. Explicitly Declare Function Return Types .................................................. 39
4.8. PORTABILITY 40
4.8.1. Case Sensitivity ................................................................................... 40
4.8.2. System Dependent Parameters and Platform Specific Code......................... 40
4.8.3. C / C++ Language Structures ................................................................ 40
4.8.4. Bit Fields............................................................................................. 40
4.8.5. Register Variables ................................................................................ 41
4.8.6. Pointer Variables .................................................................................. 41
4.8.7. Use Consistent Variable Names .............................................................. 41
4.8.8. Recursion............................................................................................ 41
4.8.9. Prefer Syntactic Constructs to Library Functions........................................ 41
4.8.10. Use const wherever possible. ................................................................. 41
4.8.11. Use Null Terminated Strings................................................................... 42
4.8.12. Always compile at the highest severity level. ............................................ 42
4.8.13. Global Variables ................................................................................... 42
4.9. C++ Specific Guidelines 42
4.9.1. Access Specifiers.................................................................................. 42
4.9.2. Ordering is: public, protected, private ..................................................... 43
4.9.3. Copy Constructor and Assignment Operator ............................................. 43
4.9.4. Inheritance of Implementation and Interface............................................ 43
4.9.5. Virtual Destructors ............................................................................... 43
4.9.6. Do not Mix printf and cout ................................................................... 44
4.9.7. Pure Virtual Functions ........................................................................... 44
4.9.8. Operator Overloading ........................................................................... 44
4.9.9. FRIEND Classes and Functions ............................................................... 44

ADITI/QMS/STDC++/1.0 Page 3 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

4.9.10. Avoid Overloading on a Pointer and Numeric Type..................................... 45


4.9.11. Never Redefine an Inherited Non-virtual Function ..................................... 45
5. Best Practices .................................................................................. 45
5.1. Use #if Not #ifdef 45
5.2. Use of Ternary Operators 46

ADITI/QMS/STDC++/1.0 Page 4 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

1. Purpose
The objective of this case study is to provide a set of standards for 'C/C++'
programming to produce software that is:

Maintainable
Reliable
Portable
Consistent
Re-usable

2. Scope
The Scope of this procedure is to set out guidelines for use in software
development and the extent of use of this guidelines is to the discretion of the
project manager. C++ Programming Standards is a set of standards to be used by
programmers while developing application/system software in 'C/C++' language.

This case Study can also act as a starting point for creating and tailoring 'C++'
programming standards specific to any project.

'C' being a subset of 'C++', this document also contains guidelines and standards
valid for C programming.

3. Definitions And Acronyms


There Are No Unique Terms Or Acronyms In This Document.

4. Guidelines
4.1. Coding Guidelines
4.1.1. Introduction
The rules specified in this section are meant to:

Improve the readability of the code


Specify a set of program formatting standards
Ensure visual consistency across programs written by different
programmers on the same project
Specify a set of rules which can be used for writing software so that
the programs in a project can be 'visually beautified'

ADITI/QMS/STDC++/1.0 Page 5 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

4.1.2. Indentation
One level of indentation will be 4 columns. This means that text on
the indented line will start on the fifth column, relative to the
starting column of previous indentation level.

Example:

if (iLineNumber > MAX_LINES_PER_PAGE)


{
XyzPageSkip (); // This is indented by one level
}

4.1.3. Functions
The following rules will ensure that function blocks are visually
demarcated in a scan of the listing of any program:

The prototype of all non-member functions should be declared


in one header file and that should be # included in the
implementation file.
For global non-member functions, specify the scope, type and
function name on one line starting on column 1. In the
declaration of a member function of a class, the scope and type
should come in one line indented by one level, relative to the
class name and the name of the class, the resolution operator
and the member function name should come aligned with the
scope and type.
Specify the open and close braces of a function on a new line
starting on column 1. Do not specify anything else on those
lines.
Indent the body of function and the definition of local variables
by one level.
Leave one blank line between logical groups of statements
within a function. Leave one blank line between declaration of
local variables and function body.
Define all local variables in a block at the top of the function.
In the argument list, only one argument should be given per
line.
These arguments, which appear in consecutive lines after the
function name should be intended by one level.
The opening parenthesis should be given on the line containing
the function name.
Closing parenthesis should be given on the line containing the
last argument.

ADITI/QMS/STDC++/1.0 Page 6 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

No arguments should be given on the line containing the


function name. The only exception is the function taking only
void. In that case, the argument (void) can be given on the
same line.
A function which doesn't take any arguments should explicitly
be defined to take void as argument.
Every function should be preceded and followed by a single
blank line.
Methods should limit themselves to a single page of code.
The Global (non-member) functions should be called by the
scope resolution operator (::)
Examples :

char* CGetReportName (
char * pchReport // comment
)
{
char * pchRep; // comment
int iLineCount; // comment
int .....; // comment

while (.........................)
{
if (....................)
{
.....
}
else
{
......
}
....
.....
}
return pchRep;
}

4.1.4. Use of Spaces

a) Leave a single space before and after an operator, except in the


following cases:

(i).The operator '->' : Do not leave any space before and after
the operator.

(ii).The operator '.' : Do not leave any space before and after the
operator.

b) Leave single space after a comma.

ADITI/QMS/STDC++/1.0 Page 7 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

c) With parenthesis, leave spaces intellectually so that the


semantics is clear and the readability is enhanced.
Examples :

iSum = ( (iFirst + iSecond) / iThird ) * iFourth ;


oCancelButton.Press () ;
iResult = sqrt( (5 + 7) * 100 ) ;

d) In an array declaration, it is preferred to # define the size of the


array and leave a space between the array name and the left
(square) bracket, except, in the case when the subscript inside
the square bracket is a simple variable (and not an expression),
the space between the array name and the left bracket may be
omitted.

Examples :

szFriend = pszNames[1] ;
szBestFriend = pszNames [(iStart + iOffset)] ;
iSum = ( (iFirst + iSecond) / iThird ) * iFourth ;
oCancelButton.Press () ;
iResult = sqrt( (5 + 7) * 100 ) ;

#define MAX_SIZE 50
int szName[MAX_SIZE] ;

e). Leave single spaces before and after a semicolon (;). If the
semicolon ends a statement, no space is required after the
semicolon.

4.1.5. Variable Declaration

a). Do not declare more than one variable in a line with a comment
on the same line.
b). Align variable names vertically, as far as possible.
c). Declare all related variables together.
Example :

int iLineLength; // length of line


int iNumberOfLines; // number of lines
char achLine[MAX_LEN]; // line width......

4.1.6. Class Declaration

ADITI/QMS/STDC++/1.0 Page 8 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

The classes should be declared in .h files and implementation


should be in .cpp file. The names should be identical for both
the files.
The opening and closing braces should be vertically aligned
with the class name.
Nested classes should be indented by one level.
Access specifiers should be indented by one level further down
from the class name.
Data members and member functions should be indented by
one level further down from the access specifiers.
Declare all the data members first. Then declare the member
functions.
If the class has more than one base classes, every base class
should be given in a separate line. The Example is Shown
below:
Examples :

class CButton : public CComponent,


protected CEdit,
private CWindow
{
public : // public member functions

int iXCoordinate ; // ...


int iYCoordinate ; // ...
int Press () ; // The button is pressed
CButton () ; // Default constructor
~CButton () ; // Destructor

protected : //Protected data members


CComponent * poOwner // ...

private : // Private Data Member Functions


VisualEffect () ; // ...

...
};

class CCircularButton : public CButton,


public CCircle
{
public : // public member functions
int iXCoordinate ; // ...
int iYCoordinate ; // ...
CCircularButton () ; // Default constructor
~CCircularButton () ; // Destructor
...
};

ADITI/QMS/STDC++/1.0 Page 9 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

This example only illustrates the organization and indentation of


the base class specification, data members, member functions and
access specifiers in a class declaration.

4.1.7. Expressions

a) If long expressions are being broken up across lines, align sub


expressions.
b) Make use of parenthesis in expressions to:
1. Identify logical grouping and
2. Reduce precedence dependence, to make the expression
easily readable.

Example:

if ( (chInput >= LOW_CHAR_SMALL &&


chInput <= HIGH_CHAR_SMALL) ||
(chInput >= LOW_CHAR_CAP &&
chInput <= HIGH_CHAR_CAP) )
{
iCharType = LETTER ;
}
else
{
if (chInput >= LOW_DIGIT &&
chInput <= HIGH_DIGIT)
{
iCharType = DIGIT ;
}
else
{
iCharType = OTHER ;
}
}
return ( iCharType ) ;

4.1.8. The Loop statements

Leave a space before and after a ';' in the head of a for


statement, to separate out the three expressions.

Example :
for ( iValue = LOW_LIMIT ; iValue <= HIGH_LIMIT ;
iValue++ )
{
cout << .... ;
}

ADITI/QMS/STDC++/1.0 Page 10 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

If all the three expressions do not fit into the same line, put one
in each line, indenting the second and the third to align with the
start of the first expression.
Examples :

for ( <expression-1> ;
<expression-2> ;
<expression-3> )
{
...........
...........
}

4.1.9. Use of goto,continue,break


Goto statements:

Goto statements should be used sparingly, as in any


well-structured code.
The goto debates are boring so we won't go into
them here.
The main place where they can be usefully
employed is to break out of several levels of switch,
for, and while nesting, although the need to do such
a thing may indicate that the inner constructs should
be broken out into a separate function, with a
success/failure return code.

for (...)
{
while (...)
{
...
if (disaster)
goto error;
}
}
...
error:

When a Goto is necessary the accompanying label


should be alone on a line and to the left of the code
that follows. The Goto should be commented
(possibly in the block header) as to its utility and
purpose.

Continue and Break statements:

ADITI/QMS/STDC++/1.0 Page 11 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

Continue and break are really disguised gotos so


they are covered here.
Continue and break like goto should be used
sparingly as they are magic in code. With a simple
spell the reader is beamed to god knows where for
some usually undocumented reason.

The two main problems with continue are:

It may bypass the test condition


It may bypass the increment/decrement expression

Consider the following example where both problems occur:

while (TRUE)
{
...
// A lot of code
...
if (/* some condition */) {
continue;
}
...
// A lot of code
...
if ( i++ > STOP_VALUE) break;

4.1.10. The switch statement

The opening and closing braces for the switch should come
vertically aligned with the switch.
The cases should come indented by one level, relative to the
switch. The opening and closing braces of case should come
vertically aligned with case.
The default case should always be present and trigger an error
if it should not be reached, yet is reached.
Example :

switch ( iCode )
{
case MAX_CUR :
{
...
break;
}

case MIN_CUR :
{
...

ADITI/QMS/STDC++/1.0 Page 12 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

break;
}

case NO_OPT :
{
...
break;
}
....
....
default :
{
......
......
}
}
}

4.1.11. The return statement

If a value is being returned with the return statement, use


parentheses to enclose the return value.
Example:
return ( TRUE ) ;

4.1.12. Initialize all Variables

You shall always initialize variables. Always. Every time.


More problems than you can believe are eventually traced
back to a pointer or variable left uninitialized. C++ tends to
encourage this by spreading initialization to each
constructor

4.1.13. Init Idiom for Initializing Objects

Objects with multiple constructors and/or multiple


attributes should define a private Init() method to initialize
all attributes. If the number of different member variables is
small then this idiom may not be a big win and C++'s
constructor initialization syntax can/should be used.

When using C++'s ability to initialize variables in the


constructor it's difficult with multiple constructors and/or
multiple attributes to make sure all attributes are initialized.
When an attribute is added or changed almost invariably
we'll miss changing a constructor.

ADITI/QMS/STDC++/1.0 Page 13 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

It's better to define one method, Init () that initializes all


possible attributes. Init () should be called first from every
constructor.

The Init () idiom cannot be used in two cases where


initialization from a constructor is required:

Constructing a member object

Initializing a member attribute that is a reference


Example

class Test
{
public:
Test()
{
Init(); // Call to common object initializer
}

Test(int val)
{
Init(); // Call to common object initializer
mVal= val;
}

private:
int mVal;
String* mpName;

void Init()
{
mVal = 0;
mpName= 0;
}
}

Since the number of member variables is small, this might be better


written as:
class Test
{
public:
Test(int val = 0, String* name = 0)
: mVal(val), mpName(name) {}
private:
int mVal;
String* mpName;
};

ADITI/QMS/STDC++/1.0 Page 14 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

4.1.14. A Line Should Not Exceed 78 Characters

Lines should not exceed 78 characters.


Even though with big monitors we stretch windows wide
our printers can only print so wide. And we still need to
print code.
The wider the window the fewer windows we can have on
a screen. More windows is better than wider windows.

4.2. Naming Conventions

4.2.1. Naming Macros

#define's and macro names should be defined using capital


letters exclusively.
The underscore character is allowed in macro names but should
be avoided as the first character of a public macro.
Avoid trying to trick the reader into thinking a macro is a
function by using the naming convention for functions when
naming a macro. This rule even applies to cases where one
wants to replace the functionality of an existing function.
Either rewrite the function or replace all calls to the function
with macro invocations.

Example:

Good:

#define MAX_LINE_LEN 80
#define DOIT(x) ( (x) + 1 )
#ifdef SPECIAL
#define STRCPY (t,s) MyStrCpy (t , s)
#else
#define STRCPY (t,s) strcpy (t , s)
#endif
...
STRCPY ( pszTarget , pszSource ) ; // Macro used for string
copy

Bad:

#define Max_line_len 80
#define DOIT(x) ( (x) + 1 )
#ifdef SPECIAL
#define strcpy (t,s) MystrCpy (t , s)
// attempt to replace standard strcpy
#endif
...
strcpy ( pszTarget , pszSource);

ADITI/QMS/STDC++/1.0 Page 15 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

4.2.2. Naming of Classes

Class names should be prefixed by the letter capital C


Use upper case letters as word separators, lower case for the
rest of a word
No underbars ('_')
Now that name spaces are becoming more widely
implemented, name spaces should be used to prevent class
name conflicts among libraries from different vendors and
groups.
Use the namespace name, which is related to the module.

Example

namespace Customer
{
class CNameOneTwo
class Cname
}

4.2.3. Variable Naming

All variables names must begin with a prefix that follows


Hungarian Notation followed by underscore. These have
become a common coding practice in Win32 programming.
They include variable prefix notations that give to variable
names a suggestion of the type of the variable
No part of the prefix should be capitalized.
All intrinsic data types and most operating system data types
have standard prefixes assigned to them. These standard
prefixes are often documented in sample code that illustrates
the use of operating system API calls. Use the standard
prefixes; do not invent your own even if you do not agree with
the standard prefix. In cases, where you have to assign
prefixes to your own data types, select a unique prefix and be
consistent!
If a variable is defined in any scope other than local scope,
chances are good that it should be prefixed. Stated another
way, all variables in file scope and function scope must be
prefixed; only simple variables in local scope may avoid the
prefix.
Class member variables should be prepended with mpr for
private/protected variables and mpb for public variables then
follow the specification for variables
You must capitalize each new word in a variable name.

ADITI/QMS/STDC++/1.0 Page 16 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

4.2.4. Hungarian Notation Prefixes

Prefix Data Types


a Array
ap Array of pointers
by Unsigned Char(byte)
c Count
ch Character
cr Color reference value
dw Unsigned long ( DWORD)
f Boolean flag
fb Flags stored in a byte
fl Flags stored in a long
fn Function
fs Flags stored in a short
ft Float
g global
hab Handle to an anchor block
hmenu Handle to menu
hps Handle to a presentation space
hvps Handle to a VIO presentation space
hwnd Handle to a window
i Index or integer
id Identifier (usually an integer)
l Long
lp long pointer
o Object of any class
off Offset. Used for values that represent
offsets from the beginning of a buffer or
structure.
p Pointer
pb Pointer to a byte
pch Pointer to a character
pfn Function pointer
pst Structure pointer
psz Pointer to an array of characters
terminated with a null character ('\O').
Also known as a pointer to a null
terminated string.
s Short
sz Array of characters terminated with a
null character ('\O')
tm Text Metric
u Unsigned Interger
uch Unsigned character
ul Unsigned long
us Unsigned short
w WORD(unsigned short)
x,y Coordinates(short)

ADITI/QMS/STDC++/1.0 Page 17 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

Example:

UNSHORT usMyVariable ; // "us" prefix for USHORT


PSZ pszMyString ; // "psz" prefix for PSZ
BYTE abyMyByteArray [] ; // "ab" prefix for an array of BYTEs
GUIButton oButton ; // "o" prefix for an object
GUIButton aoButton [] ; // "ao" prefix for array of objects

4.2.5. Naming Methods

You must capitalize each new word in a function name.


Usually every method and function performs an action, so the
name should make clear what it does: CheckForErrors() instead
of ErrorCheck(), DumpDataToFile() instead of DataFile(). This
will also make functions and data objects more distinguishable.

Underscores are not allowed anywhere in a function name
except as the first character of a private name.
Example:

Good:

OpenFile() ;
CloseFile() ;
DoFunction() ;
poMyObject->MoveRight( 10 ) ;

Bad:

xyzOpen() ; // Prefix not capitalized


Xyz_open ; // "_" not allowed in function name

4.2.6. Naming Structures and Type Definitions

Structure, type definition, union, enumeration names should be


completely capitalized. Prefix the structure name with the
word tag
When declaring a type name for a structure, the typedef name
and structure name should be the same except for the addition
of the tag in the first position of the structure name. When
declaring a pointer or array type, use the Hungarian prefix on
the type name, and capitalize the prefix.
Example:

typedef struct tagMYSTRUCT // "_" in 1st position of


// structure name

ADITI/QMS/STDC++/1.0 Page 18 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

{
USHORT usFieldOne;
BYTE byFieldTwo;
} MYSTRUCT // Type name similar to structure
name
typedef MYSTRUCT *PMYSTRUCT;
// Hungarian prefix "P" on
// pointer type

4.2.7. Global Constants

Global constants should be all caps with '_' separators.


It's tradition for global constants to named this way. You must
be careful to not conflict with other global #defines and enum
labels.
Example

const int A_GLOBAL_CONSTANT= 5;

4.2.8. Global Variables

Global variables should be prepended with a 'g'.


It's important to know the scope of a variable.

Example
Logger gLog;
Logger* gpLog;

4.2.9. Reference Variables and Functions Returning References


References should be prepended with 'r'.
The difference between variable types is clarified.
It establishes the difference between a method returning a
modifiable object and the same method name returning a non-
modifiable object.
Example

class Test
{
public:
void DoSomething(StatusInfo& rStatus);

StatusInfo& rStatus();
const StatusInfo& Status() const;

ADITI/QMS/STDC++/1.0 Page 19 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

private:
StatusInfo& mrStatus;
}

4.2.10. Pointer Variables


Pointers should be prepended by a 'p' in most cases place
the * close to the pointer type not the variable name. The
idea is that the difference between a pointer, object, and a
reference to an object is important for understanding the
code, especially in C++ where -> can be overloaded, and
casting and copy semantics are important.

Pointers really are a change of type so the * belongs near


the type. One reservation with this policy relates to
declaring multiple variables with the same type on the same
line. In C++ the pointer modifier only applies to the closest
variable, not all of them, which can be very confusing,
especially for newbies.You want to have one declaration
per line anyway so you can document each variable.
Example

String* pName= new String;

String* pName, name, address; // note, only pName is a pointer.

4.3. Documentation
4.3.1. Comments
Comments are an essential, mandatory part of every program.
Every source file must have a block comment at the beginning
explaining what the file is for and these block comments must
precede every function and/or logical block of code. Line
comments must be used to clarify any line of code that could be
ambiguous. If there is any doubt whether another person will
understand what the code is doing, explain it in a comment!

It should go without saying that when a comment shares a line with


code, the comment lies to the right of the code. When comments
occupy their own line(s), the comment should be above the code it
pertains to. The indentation level of a comment (including the
comment symbols) should match that of the code it is documenting
(unless it is on the same line).

ADITI/QMS/STDC++/1.0 Page 20 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

4.3.2. Readability of Comments

Comments should be explanatory but concise. Avoid restating the


obvious.
Example:

Recommended :
if (iCurs = = 0) // If at start of list

Not Recommended :
if (iCurs = = 0) // if the cursor is zero

Recommended : Tells what this API call does for the program
DOSEnterCritSec(); // Set Crit so IDM_DONE isn't processed .
// ... until this thread has terminated

Not Recommended :
short sReturnCode = 0; // return code variable
Do not restate the obvious

4.3.3. Comments for a Block


Comments within a function that explain a group of lines must
precede the lines of code they are meant for. These comments must
be preceded by a blank line and indented by one level.

4.3.4. Inline Comments

Wherever possible, put comments that explain a single line of code


in the same line as the code itself, after leaving some space between
the end of the code and the beginning of the comment. Make sure
that these comments are aligned vertically and are within column
72. Header for an interface file Begin each header file with a
comment block of the following format :
// ******************************************************************
//
// interface : MODULE NAME
//
// ******************************************************************
// COPYRIGHT STRING
//
// PROJECT : PROJECT NAME
// MODULE : Module name
// VERSION : Version number
// AUTHOR : Name of author
// DATE : Date of initial release
// SCCS : SCCS string
// SYSTEM : Compiler / OS
// FILE : Name of this file (with relative path)

ADITI/QMS/STDC++/1.0 Page 21 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

// *******************************************************************
//
// History :
// A list of changes made to this file
//
// Purpose :
// The description of the use or purpose of this
// module (from a user standpoint)
//
// Methods :
// List names of the methods implemented in this file.
// Arguments and return values need not be mentioned.
//
// ******************************************************************

4.3.5. Header for an implementation file

Begin each source file with a block of comments of the following


format :

//A description of the implementation logic or (algorithmic logic


//of this module)
//
// methods :
// List names of the methods implemented in this file.
// Arguments and return values need not be mentioned.
//
//*****************************************************
*************

4.3.6. Function Header in the Interface File

Begin each function declaration in the header file with the a block
of comments as follows (the function comment block should
precede the function name). There should be only one function
header corresponding to all the overloaded versions of a function,
and the prototypes for all the overloaded versions should be
given immediately after this header.
// ***************************************************************
// method : Name of the function
// ***************************************************************
Prototypes for all the overloaded versions of this function

4.3.7. Function Header in the Implementation File

Begin each function (methods of classes also) in the


implementation file with the a block of comments as follows (the
function comment block should precede the function name):

ADITI/QMS/STDC++/1.0 Page 22 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

// ***************************************************************
// method : Name of the function
// **********************************************************//
*****************************************************************
//
// implementation : MODULE NAME
//
// *****************************************************************
//
// COPYRIGHT STRING
//
// PROJECT : PROJECT NAME
// MODULE : Module name
// VERSION : Version number
// AUTHOR : Name of author
// DATE : Date of initial release
// SCCS : SCCS string
// SYSTEM : Compiler / OS
// FILE : Name of this file (with relative path)
// *****************************************************************
//
// History:
// A list of changes made to this file
//
// implementation :
*****
// return value :
// A description of the return value of this function.
//
// purpose :
// A description of the use of this function.
//
// possible errors :
// List the limitations, possible errors in use, and the
// exceptions.
//
// Implementation :
// Describe the implementation logic of this function
// ***************************************************************

4.3.8. Function Documentation in the Documentation File

We use the format of UNIX man pages for the documentation of


functions in the documentation file. Each function public function
should be documented in the documentation file, in the following
format.
// ***************************************************************
// method : Name of the function
// ***************************************************************
SYNOPSIS :

ADITI/QMS/STDC++/1.0 Page 23 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

The name of the required include file. (optional)


Function prototype.

DESCRIPTION :
A description of the use or purpose of this function

RETURN VALUE :
A description of what is returned by this function. Here,
we explain not just the return type, but the actual
significance of the return value.

ERRORS :
A description of the possible errors with this function, restrictions in
usage, etc.

4.3.9. Preprocessor Directives


Each #else and #endif, if far from the corresponding #if, must have
the condition of the #if as a comment.
Example :

#ifdef ORACLE
....
....
#endif // ORACLE

4.3.10. Directory Documentation

Every directory should have a README file that covers:

the purpose of the directory and what it contains


a one line comment on each file. A comment can usually be
extracted from the NAME attribute of the file header.
cover build and install directions
direct people to related resources:
directories of source
online documentation
paper documentation
design documentation

4.4. Program structure

4.4.1. Size of Files


A program source should have a maximum of 1000 lines
(comments + code). In case a source program is larger than 1000
lines, examine it critically and try to break it up into smaller source

ADITI/QMS/STDC++/1.0 Page 24 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

files, removing the lower level commonly used functions into other
files.

4.4.2. Size of Functions


A function should not have a more than 60 lines (code +
comments). Examine all functions longer than 60 lines critically.
There usually are ways of compacting/ breaking up the function.
Exceptions would be functions with one or more large switch
statements.

4.4.2.1 Format of a Source File

The contents of a source file (*.cc file) is to be organized in the


following format.

// ************************************************************
//
// implementation : MODULE NAME
//
// ************************************************************
//
// COPYRIGHT STRING
//
// PROJECT : PROJECT NAME
// MODULE : Module name
// VERSION : Version number
// AUTHOR : Name of author
// DATE : Date of initial release
// SCCS : SCCS string
// SYSTEM : Compiler / OS
// FILE : Name of this file (with relative path)
// ************************************************************
//
// History:
// A list of changes made to this file
//
// Implementation :
// A description of the implementation logic for this
// module (class)
//
// methods :
// List names of the methods (functions) implemented
// in this module.
// Arguments and return values need not be mentioned
here.
//
// Friend functions :
// A list of all the friend functions of this class
//
// ************************************************************
//
// interface

ADITI/QMS/STDC++/1.0 Page 25 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

// *********
All the includes for this source file

// global constants
// ****************
All the global constants for this source file

// global types
// ************
All the global types for this source file

// global macros
// *************
All the global macros for this source file

// private methods
// ***************
All the private member functions are implemented here

// protected methods
// *****************
All the protected member functions are implemented here

// exported methods
// ****************
All the exported are member functions implemented here

// End of File File Name

4.4.3. Format of an ASCII Documentation File

The contents of the documentation file for any module is to be


organized in the following format.

General Description:
A general description of the functionality of this
module

General Topics:

Issues, concepts and terms dealt with, in this module


For example, in a module for memory management,
the following can be explained :
garbage collection
compaction
dynamic allocation etc.

Restrictions:

******************************************************************
//
// documentation : MODULE NAME

ADITI/QMS/STDC++/1.0 Page 26 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

//
// ******************************************************************
//
// COPYRIGHT STRING
//
// PROJECT : PROJECT NAME
// MODULE : Module name
// VERSION : Version number
// AUTHOR : Name of author
// DATE : Date of initial release
// SCCS : SCCS string
// SYSTEM : Compiler / OS
// FILE : Name of this file with relative path
// ******************************************************************

Module Name :

Class Name :

Interface File :

Error File :

Implementation File :

Library :

Maturity Index :

Base Classes :

Imported Modules :

Imported Classes :

Friend Classes :

Friend Functions :
this module

Attribute List:
-Protected
All the protected data members
-Public
All the public data members

Service list:

- Protected:
Name of all the protected member functions
- Public:
Names of all the public member functions

Description of Services:

ADITI/QMS/STDC++/1.0 Page 27 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

- Protected :
Describe all the protected member functions.
The description should include the names of the
member functions, an explanation of the purpose,
arguments, and return values.

-public :
Describe all the protected member functions.
The description should include the names of the
member functions, an explanation of the purpose,
arguments, and return values.

// End of file File Name

4.4.4. Extern Declarations


Do not put extern declarations inside a function. Collect them all
and put them at the top of the file, immediately after the #includes.

4.4.5. Multiple Levels of Control Structures


More than three levels of combination of if...else, do...while, while,
etc, within the code is generally a sign of potential trouble and
should not be present.

4.4.6. Static and Extern


Define all local functions as 'static'.
Define all global variables as either static or extern.

4.4.7. Error Handling, Dates and Reports


For the whole project, create and use common functions for error
handling, date handling, report writing, etc.

4.4.8. Naming Class Files

4.4.9. Class Definition in One File


Each class definition should be in its own file where each file is
named directly after the class's name

Example ClassName.h

4.4.10. Implementation in One File


In general each class should be implemented in one source file:
ClassName.cc

ADITI/QMS/STDC++/1.0 Page 28 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

4.5. Programming Construct

4.5.1. Goto Statements


Use of the goto statement is strictly prohibited. This statement may
create hidden loops within the program and results in unreadable
and unmaintainable code.

4.5.2. Continue and Break


Use the continue and break constructs with care. Using these in
nested loops can make code difficult to follow.

4.5.3. Return and Exit


Every function should end with a return statement, avoid the use of
exit.

4.5.4. Void Functions


Declare all functions that do not return any value as void.

4.5.5. Malloc Family of Functions


Avoid the use of the malloc() family of functions as far as possible.
Prefer new() and delete() to malloc() and free(). Use malloc()
family of functions only when you are implementing your own
new(). Calls to malloc() family of functions should always be
checked for error return and typedefed to the proper 'lvalue'.

4.5.6. I / O Functions
Calls to I/O functions should always be checked for error returns.

4.5.7. Boolean Type


Define a BOOLEAN type to take care of flag variables and
functions that return TRUE or FALSE condition.

4.5.8. Floating Point Constants


If a floating point constant is required, mention it explicitly, even if
it has no decimal values. Example:

#define MONTHS_IN_YEAR 12.0

4.5.9. #define for Expressions


In a #define, if the replacement text is an expression, enclose the
whole text within parenthesis as shown below:

ADITI/QMS/STDC++/1.0 Page 29 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

#define LEFT_MARGIN 5
#define RIGHT_MARGIN (LEFT_MARGIN + 65)

4.5.10. switch Statements


Every switch statement should have a default case (with just a
break, if no action is to be taken).

4.5.11. Required Methods for a Class


Almost all classes should implement the following methods. If you
don't have to define and implement any of the "required" methods
they should still be represented in your class definition as
comments.

Default Constructor

If your class needs a constructor, make sure to provide one. You


need one if during the operation of the class it creates something or
does something that needs to be undone when the object dies. This
includes creating memory, opening file descriptors, opening
transactions etc.

If the default constructor is sufficient add a comment indicating


that the compiler-generated version will be used.

If your default constructor has one or more optional arguments,


add a comment indicating that it still functions as the default
constructor.

Virtual Destructor

If your class is intended to be derived from by other classes then


make the destructor virtual.

Copy Constructor

If your class is copyable, either define a copy constructor and


assignment operator or add a comment indicating that the
compiler-generated versions will be used.

If your class objects should not be copied, make the copy


constructor and assignment operator private and don't define
bodies for them. If you don't know whether the class objects
should be copyable, then assume not unless and until the copy
operations are needed.

ADITI/QMS/STDC++/1.0 Page 30 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

Assignment Operator

If your class is assignable, either define a assignment operator or


add a comment indicating that the compiler-generated versions will
be used.

If your objects should not be assigned, make the assignment


operator private and don't define bodies for them. If you don't know
whether the class objects should be assignable, then assume not.

4.5.12. Justification

Virtual destructors ensure objects will be completely


destructed regardless of inheritance depth. You don't have
to use a virtual destructor when:
You don't expect a class to have descendants.
The overhead of virtualness would be too much.
An object must have a certain data layout and size.
A default constructor allows an object to be used in an
array.
The copy constructor and assignment operator ensure an
object is always properly constructed.

Example using default values:

class Planet
{
public:
// The following is the default constructor if
// no arguments are supplied:
//
Planet(int radius= 5);

// Use compiler-generated copy constructor, assignment, and


destructor.
// Planet(const Planet&);
// Planet& operator=(const Planet&);
// ~Planet();
};

4.5.13. Use the Same Form in Corresponding Calls to new and delete

If you use new with [ ] for creating an array, use [ ] with delete
for properly deleting the array. If you do not use [ ] with new do
not use [ ] with delete.

Example :

ADITI/QMS/STDC++/1.0 Page 31 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

XYZString * pString = new XYZString ;


XYZString * paString = new XYZString[100] ;
...
delete pString ;
delete [] paString ;

4.5.14. Don't Over Use Operators

C++ allows the overloading of all kinds of weird operators.


Unless you are building a class directly related to math there
are very few operators you should override.
Only override an operator when the semantics will be clear to
users.
Very few people will have the same intuition as you about
what a particular operator will do.

4.5.15. Open/Closed Principle


The Open/Closed principle states a class must be open and closed
where:

open means a class has the ability to be extended.


closed means a class is closed for modifications other than
extension. The idea is once a class has been approved for use
having gone through code reviews, unit tests, and other
qualifying procedures, you don't want to change the class very
much, just extend it.

The Open/Closed principle is a pitch for stability. A system is


extended by adding new code not by changing already working
code. Programmers often don't feel comfortable changing old code
because it works! This principle just gives you an academic
sounding justification for your fears.

4.5.16. Use of Namespaces


Namespaces are now commonly implemented by compilers. They
should be used if you are sure your compiler supports them completely.

4.5.16.1. Naming Policy

There are two basic strategies for naming: root that name at
some naming authority, like the company name and
division name; try and make names globally independent.

ADITI/QMS/STDC++/1.0 Page 32 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

4.5.16.2. Don't Globally Define using

Don't place "using namespace" directive at global scope in


a header file. This can cause lots of magic invisible
conflicts that are hard to track. Keep using statements to
implementation files.

4.5.16.3. Use Header File Guards

Include files should protect against multiple inclusion


through the use of guards:

#ifndef ClassName_h

#define ClassName_h

#endif // ClassName_h

Replace ClassName with the name of the class contained in


the file. Use the exact class name. Some standards say use
all upper case. This is a mistake because someone could
actually name a class the same as yours but using all upper
letters. If the files end up be included together one file will
prevent the other from being included and you will be one
very confused puppy. It has happened!

Most standards put a leading _ and trailing _. This is no


longer valid as the C++ standard reserves leading _ to
compiler writers.

When the include file is not for a class then the file name
should be used as the guard name.

4.6. Data Usage

4.6.1. Employ Narrowest Possible Scope

Variables and classes should be defined in a scope that is as


close as possible to the scope in which they are used.

There are three possible levels for scoping: local, function,


and file. Local scope involves a block within a function,
and a variable declared in local scope is visible only inside
the enclosing block:

ADITI/QMS/STDC++/1.0 Page 33 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

int XYZMyFunction ( void )


{
if ( XYZTest ( ) )
{
int i;
for ( i = 0 ; i < MAXLENGTH ; i++ )
{
// i is visible here
}
// i is visible here
}
// i is NOT visible here
}

Always try to define a variable in local scope, but if the variable


needs to be visible to a whole function, use function scope:

int XYZMyFunction ( void )


{
int fFlag; // fFlag is defined in a function scope
if ( XYZTest ( ) )
{
int i ; // i is defined in a local scope
for ( i = 0 ; i < MAXLENGTH ; i++ )
{
// i is visible here
// fFlag is visible here
}
// i is visible here
// fFlag is visible here
}
// i is NOT visible here
// fFlag is visible here
}

If a symbol needs to be visible to multiple functions within the


same file, use file scope but define the symbol as static :
static int iMyCounter = 0 ; // iMyCounter is defined
// in file scope
...
void main ( )
{
// iMyCounter is visible here
}

int XYZMyFunction ( void )


{
if ( XYZTest ( ) )
{
iMyCounter =+ iNewData ; // iMyCounter is visible
// here
}
}

ADITI/QMS/STDC++/1.0 Page 34 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

int ABCMyOtherFunction ( void )


{
int iNewAmount , iOldAmount ;
// iMyCounter is visible here
iNewAmount = iOldAmount * iMyCounter ;
return (TRUE) ;
}

If a symbol needs to be visible to multiple functions within multiple


files (this is also known as public scope), use file scope, and do
NOT define the symbol as static:
int iMyCounter ; // iMyCounter is visible
// in this file as well
// as being visible in
// any other file that
// is linked with this file.
...
void
main ()
{
}

4.6.2. Do Not Define Data Types with #define


Do not use #define for data type definition. Use typedef
instead.

Using #define to declare data types can lead to unexpected


errors. A typedef is explicitly designed for the purpose of
declaring data types.

Example:

Good:

typedef int WEEK, *pWEEK ;


WEEK Weekday ;
PWEEK pwkStartWeekday , pwkEndWeekday ;

Bad:

#define WEEK int


#define WEEK int *
WEEK Weekday ;
pWEEK pwkStartWeekday, pwkEndWeekday ;
// error - pwkEndWeekday
// will be defined as an
// int and not as an
// int*

ADITI/QMS/STDC++/1.0 Page 35 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

4.6.3. Simulate Scope for Macros

When defining constants and macros that must be restricted to a


narrower scope than file scope, do stimulate scoping rules by undefining
the constant or macro in a location that corresponds to the normal scoping
rules. It is not necessary to undefine constants defined at the file "scope".

Example:

int
XYZMyFunction ( void )
{
#define BUFSIZE 128

{
#define MYADD (a,b) ( ( a ) + (b) + 1 )
...
#undef MYADD // make MYADD invisible, simulating
// local scope
}
return ( 0 ) ;
#undef BUFSIZE // make BUFSIZE invisible,
simulating
// function scope
}

4.7. Programming Style

4.7.1. Do Not Redefine Standard Items


Do not redefine items which are included in standard header files.
Example : Very bad

#define NULL 0
#define TRUE 1
#define FALSE 0

4.7.2. Do Not Alter the Language

Do not redefine standard operators or keywords. Do NOT attempt


to simulate another language.
Example:

Bad :

#define EQUAL ==
#define NOTEQUAL !=
#define GREATERTHAN >

ADITI/QMS/STDC++/1.0 Page 36 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

Very Bad :

#define begin {
#define end }
#define repeat do
#define until while

Note :

By defining new classes and operations on classes, you are not


altering the language, but only enhancing it.

4.7.3. Use Straightforward Coding Style


Make your statements straightforward and concise. Do not use
obscure functions and expressions if a more understandable
method exists.

Example:

Good :

#define ROUNDINGFACTOR 3
int iSum = iXOne + iXTwo;
int iResult = (iSum * iSum);
iRounded Result = ( iResult + ROUNDINGFACTOR ) &
~ROUNDINGFACTOR;

Bad :

iRoundedResult = ( ( (iXOne + iXTwo) *


(iXOne + iXTwo) ) +
ROUNDINGFACTOR ) &
~ROUNDINGFACTOR ;

4.7.4. Explicitly Code Boolean Expressions


Do not rely on implicit conversion rules to convert an integer type
to a boolean. Always explicitly code a boolean expression.

Example :

Good :

if ( iX ! = 0 )
{
.... ;
}
fCanIProceed = (iCursor > 0 ) ;

Bad :

ADITI/QMS/STDC++/1.0 Page 37 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

if ( iX )
{
.... ;
}
fCanIProceed = iCursor ;

4.7.5. Observe Operator Precedence Rules

Do not expect the reader to know precedence rules beyond the


usual mathematical rules for associativity and commutativity. Do
not expect the reader to know precedence rules for operators. Use
parentheses to clarify the execution sequence in the code.

The various precedence levels and associatively directions can


make understanding the evaluation sequence of an expression
difficult. Therefore, it is safest not to expect the reader to know
precedence rules for operator to understand the intended logic for a
piece of code. Using parentheses to explicitly state the execution
sequence adds clarity to an expression. Certainly, if a
misunderstanding of precedence rules would result in a
misunderstanding of the logic, parenthesize the code!

4.7.6. Operator Precedence Table

To facilitate the conversion of unparenthesized code into


parenthesized code and for completeness, the following table
contains a list of operators by precedence. Higher precedence
operators appear before lower precedence operators. For each
operators, the associativity direction is indicated.
Precedence and associativity rules determine the sequence of
evaluation within an expression.
Where an expression contains two operators that have different
precedence levels, the precedence levels of the operators determine
the evaluation sequence.
Where an expression contains two operators that have similar
precedence levels, the associativity rules determine evaluation
sequence.
Operators may either associate left to right, which is more often the
case, or they may associate right to left.
Unary operators, the conditional statement, and assignment
operators associate from right to left.
All other operators associate from left to right.
Another way of thinking of right to left associativity is inside-to-
outside associativity.

ADITI/QMS/STDC++/1.0 Page 38 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

A precedence and associativity table is given below. Each box


holds operators with the same precedence. An operator has higher
precedence than operators in lower boxes. For example: a+b*c
means a+(b*c) because, * has higher precedence than +, and a+b-c
means (a+b)-c because + and - have the same precedence (and
because + is left associative).
Precedence Table

Operator Commonly used name Example Associativity


:: scope resolution className::member
:: global ::name
. member selection object.member
-> member selection pointer->member
[] subscripting pointer [expr]
() function call expr (exprList)
() value construction type (exprList)
++ post increment lvalue++
-- post decrement lvalue--
Sizeof size of object sizeof expr
Sizeof size of type sizeof type
++ pre increment ++lvalue
-- pre decrement --lvalue
~ complement ~expr
! not !expr
- unary minus -expr
+ unary plus +expr
& address of &lvalue
* dereference *expr
new create (allocate) new type
Delete destroy (deallocate) delete pointer
Delete[] destroy array delete[] pointer
() cast (type conversion) (type) expr
.* member selection object.*pointerToMember
-> member selection pointer->*pointerToMember
* multiply expr * expr
/ divide expr / expr
% modulo (remainder) expr % expr
+ add (plus) expr + expr
- subtract (minus) expr - expr

4.7.7. Explicitly Declare Function Return Types

Always declare a return type for a function. If the function returns


nothing, define it returns type as void.
Example:

Good:

// Explicit return type declared

ADITI/QMS/STDC++/1.0 Page 39 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

void XYZQueryLength ( void ) ;

Bad:

// No explicit return type declared


XYZQueryLength( void );

4.8. PORTABILITY
4.8.1. Case Sensitivity
Do not assume that the linker is case sensitive. Define variables
and functions to be unique in a case insensitive environment.

4.8.2. System Dependent Parameters and Platform Specific Code


Do not hard code path names to files or directories, user
identifier numbers, log-in names, terminal lines or other
system dependent parameters. Declare these as constants in
header files or obtain them from the environment.

All code that varies between platforms (to which portability


is desired), should be in separate files with #ifdef blocks.

Bit operations can create portability problems. If essential,


define and macros with bit operations.

4.8.3. C / C++ Language Structures

The C++ or C languages defines no particular layout for storage of


items relative to each other. Due to this, there may be 'gaps'
between the elements of a structure, which are environment
dependent. Any code which accesses the data making assumptions
of the relative storage layout (union) is inherently non-portable.

4.8.4. Bit Fields

All C compilers do not implement bit fields.

There is no consistency regarding the order (left to right or


right to left) of assignment of bit fields. The use of bit
fields in unions to dissect bits from other data is non-
portable.

ADITI/QMS/STDC++/1.0 Page 40 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

4.8.5. Register Variables


Avoid the use of register variables. If essential for efficiency, use
them as local variables only.

4.8.6. Pointer Variables


Pointer variables and the results of operations on pointer variables
should not be assigned to either int, unsigned, short, or char
variables.

4.8.7. Use Consistent Variable Names

Two variables, which serve similar purposes and are defined in


non-overlapping scope, should be assigned the same name.

This rule especially applies to simple variables that are exempt


from Hungarian Notation prefixing. For example, if you use "i"
and "j" for iteration in one function, do not start using "s" and "t"
somewhere else, be consistent! Another example occurs, when a
set of related functions all must define a pointer variable to
traverse the same list of structures. The cursor variable in each
function that is used to iterate over the list should be named the
same.

4.8.8. Recursion
If recursion is used, ensure that there is a terminating statement,
and also ensure that there is convergence of the recursion. Be
careful on the effects of recursion on local static variables and
global variables. Recursion may be compact and elegant but not
necessarily more efficient, and hence could be rewritten in a non-
recursive manner, if found suitable.

4.8.9. Prefer Syntactic Constructs to Library Functions

Prefer using syntactic constructs, rather than library routines,


whenever possible.

Example:
If assignment (=) is satisfactory, do not go for memcpy () .

4.8.10. Use const wherever possible.


This protects the data from unintentional modifications inside the
program. When using const remember the following:
char * p = "HELLO" ; // variable data
// Variable pointer

ADITI/QMS/STDC++/1.0 Page 41 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

const char * p = "HELLO" ; // constant data


// Variable pointer
char * const p = "HELLO" ; // variable data
// Constant pointer
const char * const p = "HELLO" ; // constant data
// Constant pointer

4.8.11. Use Null Terminated Strings


As far as possible, use and store string values in null terminated
form. Non-null terminated strings may cause problems with
operations like string copy.

4.8.12. Always compile at the highest severity level.

This will ensure that your programs will successfully compile with
any severity level. Moreover it brings to your notice, all possible
errors and warnings.

4.8.13. Global Variables


All global variables should be defined at the start of construction
and maintained at the project level.

4.9. C++ Specific Guidelines

4.9.1. Access Specifiers


The available access specifiers are private, protected and public.
Access specifiers can be used with data members and member
functions of a class.

Public data members and member functions are accessible for all
classes and functions.

Protected data members and member functions are accessible to all


the member functions of the same class, all the derived classes and
all friend classes and functions.

Private data members and member functions are accessible only to


member functions of the same class and friend functions and
classes.

A thumb rule is that most of the data members of any class will
normally be private, and, most of the classes will contain public
member functions.

ADITI/QMS/STDC++/1.0 Page 42 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

4.9.2. Ordering is: public, protected, private


Notice that the public interface is placed first in the class, protected
next, and private last. The reasons are:

programmers should care about a class's interface more than


implementation
when programmers need to use a class they need the interface
not the implementation

4.9.3. Copy Constructor and Assignment Operator


Define a copy constructor and assignment operator for classes with
dynamically allocated memory. This will avoid potential memory
leaks.

4.9.4. Inheritance of Implementation and Interface

Understanding the difference between the inheritance of


implementation and inheritance of interface.

When we use the non-virtual member functions in a base class in


an inheritance hierarchy, both the implementaion and the interface
are inherited (by the derived class). This means that the derived
classes can respond to the same message as the base class and the
derived classes invoke the same function, in response to the
message (same implementation). In other words, the derived
classes get the same implementation as the base class, which
cannot be safely overriden.

When we use the virtual member functions in a base class in an


inheritance hierarchy, the interface is inherited, and the
implementation may be inherited. This means that the derived
classes can respond to the same message as the base class and the
derived classes get a default implementation from the base class,
which can be overriden.

When we use the pure virtual member functions in a base class in


an inheritance hierarchy, only the interface is inherited, and the
implementation will not be inherited. This means that the derived
classes can respond to the same message as the base class, but the
behaviour for the derived class should be implemented in the
derived class.

4.9.5. Virtual Destructors

ADITI/QMS/STDC++/1.0 Page 43 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

Consider making destructors virtual in base classes. This will


make sure that the proper destructor is called all the time, even if
the object is accessed through a pointer to the base class. If the
destructor is not virtual and you are accessing the object through a
pointer to the base class, only the base class destructor will be
called for destroying the object. The base class destructor may not
always be able to destroy the object properly. So making the
destructor virtual ensures that the derived class objects are
properly destroyed all the time.

4.9.6. Do not Mix printf and cout

If we mix printf and cout in the same program, we are bound to get
problems. All the output by printf will appear together and all the
output by cout will appear together.

This is because of not flushing the buffer with each output


operation. So it is recommended that you use only cout and not
printf

4.9.7. Pure Virtual Functions

Pure virtual functions means that, only the interface will be


inherited, and, the implementation will not be inherited.
This also means that, we have to reimplement the pure
virtual functions in the derived classes.

In other words, a pure virtual function provides and


interface, implementing which is the responsibility of
derived classes. Aclass which contains pure virtual
functions, will be an abstract class. In a base class, if you
identify an interface, for which, a default implementation
cannot be provided in that class, make it pure virtual.

4.9.8. Operator Overloading

Many operators are oftern overloaded in user defined classes. For


example, when you are writing some classes for vector
manipulation, or matrix operations, it will be better to use + for
addition, * for multiplicaton and so on. This make the classes feel
very friendly and familiar.

4.9.9. FRIEND Classes and Functions

ADITI/QMS/STDC++/1.0 Page 44 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

Friend classes and functions can access private data members and
member functions of a class. The use of friend may make things
confusing. So the use of friend classes and functions is not
encouraged.

4.9.10. Avoid Overloading on a Pointer and Numeric Type

Consider the situation that you have two overloaded versions of a


member functions, one taking a numeric argument and the other
taking a pointer argument. This is not a safe situation,
Example :

void
TSTDoSomething (
char * pchData ) ; // This version takes a pointer to char

void
TSTDoSomething (
int iData ) ; // This version takes an int

If we write TSTDoSomething (NULL) What will happen? Which


version of the function will be invoked? So avoid overloading on
such types.

4.9.11. Never Redefine an Inherited Non-virtual Function

Eventhough it is allowed to redefine non-virtual function in a


derived class, it is not advisible to do so. when we access the
derived class objects through a pointer to the base class object,
these can go wrong. So when you want to redefine a base class
function in the derived class, make sure that it is virtual.

5. Best Practices
5.1. Use #if Not #ifdef

Use #if MACRO not #ifdef MACRO. Someone might write code like:

#ifdef DEBUG
temporary_debugger_break();
#endif

Someone else might compile the code with turned-of debug info like:
cc -c lurker.cpp -DDEBUG=0

ADITI/QMS/STDC++/1.0 Page 45 of 46
Aditi Technologies Pvt. Ltd. C, C++ Coding Standards

Alway use #if, if you have to use the preprocessor. This works fine, and
does the right thing, even if DEBUG is not defined at all (!)

#if DEBUG
temporary_debugger_break();
#endif

If you really need to test whether a symbol is defined or not, test it with the
defined() construct, which allows you to add more things later to the
conditional without editing text that's already in the program:

#if !defined(USER_NAME)
#define USER_NAME "john smith"
#endif

5.2. Use of Ternary Operators

If it is applicable in the case of writing if..else statement use ternary


operator

Justification
Reduce the number of lines
Improve the performance
Used to form macros for checking conditions
Example

cout<<Maximum << (a > b)?a : b ;

ADITI/QMS/STDC++/1.0 Page 46 of 46

You might also like