## Introduction

Writing programs in C++ requires a thorough understanding of its language features. As C++ is a very rich language understanding all these features and applying them at the right place in programms requires a lot of experience. In these notes I try to summarize my experience in this wonderful programming language. To learn C++ one need to program, that is solve some problem with a computer.

We can not remember every detail therefore we need references:

## C++ Overview

A program consists of human readable text which we call code. The code is stored in a source file. The code must obey the formal rules of the programming language used. The source file is translated by a program, called compiler, into an object file containing only machine instructions. Another program, the linker, translates a number of object files into a machine executable file. The process of writing programs consists of: writing source code, compiling source codes into object files and then linking object files into an executable file. The steps of compling and linking are machine and vendor dependent. However the specifications of the source code are standardized by the C++ Language specification.

Although a program could be written in one source file this is in practice not done. For a C++ program two type of files are distuinguished: source files (ending with .cpp) and header files (ending with .h). A source file contains the code the computer must execute and also #include directives for including header files. The header files for system libraries are included between brackets and for private libraries between quotes. The first step of the compiler is then preprocessing the source files: a) macro processing and b) bring in the header files defined by the #include directives. The result of this preprocessing is a translation unit. A translation unit contains all the code needed for a compiler to translate the source code into machine instructions.

Machine code is essentially very simple. Each instruction consists of a reference to one or more data items and an operation on these data items. Operations can be: movement of data from one place to another, basic arithmetic and logical operations, and program flow operations.

The essence of a programming consists of two activities:
• Declare variables, that is give a name, identifier, and specify the data type for a variable.

A variable has a certain lifetime. Depending on how they are declared, some persist throughout the entire program (technically they are allocated on the heap), while others are created and destroyed dynamically as the program moves through various levels of function calls (technically they are allocated on the stack). The declaration of a variable also controls what parts of the program have access to the variable, which is called its scope. The scope of a local variable extends to the end of the block in which it is declared. The lifetime of a local variable is the time during which that block is active. If a variable declaration appears outside any function definition, that declaration introduces a global variable. The scope of a global variable is the remainder of the file in which it is declared.

The standard syntax for declaring a variable is type namelist;

In C++, the initial contents of a variable are undefined. If you want a variable to have a particular initial value, you need to initialize it explicitly. One approach is to use an assignment statement in the body of the function to assign a value to each variable before you use it. You can, however, include initial values directly in a declaration by writing an equal sign and a value after a variable name. An initial value specified as part of a declaration is called an initializer.

• Define the operations on variables and the program flow with functions and statements.

For the declaration of variables there are two classes of data types available: fundamental data types and user defined types.

#### Fundamental data types

Fundamental data types correspond to data types available at the machine level implementation.
• bool
• char
• int
• double
These data types have built in arithmetic operators:
• + plus
• - minus
• * multiply
• / divide
• % remainder
and comparison operators:
• == equal
• != not equal
• > greater than
• < less than
• >= greater than or equal
• <= less than or equal

#### User defined data types

User defined types (UDT) allows the programmer to define its own types and operations on these types. C++ has many ways to accomplish this: structures, classes, and templates. The proper way to organize the code of a user defined type is to separate the declaration from the definition. the declaration is put in a header file and the definition into a source file. The interface header file is included in both the source where the UDT is used as well as in the implementation file of the UDT.

#### Statements

Statements in C++ fall into two classes: simple statements and control statements. A simple statement consists of an expression—typically an assignment or a function call—followed by a semicolon. The control statements are:
• if
• switch
• for
• while
The first two are used to express conditional execution, while the last two are used to specify repetition.

#### Functions

C++ programs are typically subdivided into several functions. Each function consists of a sequence of statements that can be invoked by writing the name of the function,followed by a list of arguments enclosed in parentheses. These arguments are copied into the corresponding parameter variables inside the function. The function can return a result to the caller by using the return statement and can share values using reference parameters. A C++ program contains at least one function, called main. This is the first function that is executed.

Learning C++ is learning the details about available functionality on data-types, statements and functions.

## Classes

#### Class declaration

Classes are user-defined types needed to achieve a higher abstraction level than just the fundamental types. A struct is similar to a class where all members are public (no access restrictions). In a class the members are by default private (only member functions can access the member data by default), but with the access specifiers: private and public this can be modified. A class consists of member data and member functions. The member functions of a class are usually defined outside the class declaration. The function name need to be prefixed with the class name and ::. This is called scope resolution and is needed so the compiler can make the link between the class and the function. In fact, the definitions are often put in a separate file and compiled separately. The point is that application programs that use the class need only know what the objects can do; they do not need to know how the objects do it. The function declarations tell what they do; the function definitions tell how they do it. A member function defined within the class definition – rather than simply declared there – is taken to be an inline member function. That is, inclass definition of member functions is for small, frequently used functions. Instead of definining the function within the class declaration, one can alternatively define the function as an inline function after the class declaration in the same file. When the member function definitions are separated from the declarations the declaration section is called the class interface, and the section containing the member function definitions is called the implementation. The interface is the part of the class that the programmer needs to see in order to use the class.

When a class has been declared objects of this class can declared, this is called instantiation, the resulting object is called an instance of the class.


// declaration of a class
class T {                   // declaration of a class T
public:
void f(int);        // public member function
private:
int d;              // private data member
};
int main() {
T x;                    // declare variable of class T
x.f(3);                 // call the member function on instance x
}
void T::f(int _d) {         // use scope resoution
d=_d;                   // access of private data members via member function
}



#### Constructors and destructors

A class’s constructor “constructs” the class objects by allocating and initializing storage for the objects and by performing any other tasks that are programmed into the function. A constructor has the same name as the class. Multiple constructors can be defined, with different argument lists. A default constructor is a constructor that can be called without supplying an argument. If no constructors are defined explicitly the compiler will try to generate one. Because const and references must be initialized, a class containing const or reference members cannot be default constructed unless the programmer explicitly supplies a constructor.

Most constructors do nothing more than initialize the object’s member data. Consequently, C++ provides a special syntactical device for constructors that simplifies this code. The device is an initialization list. The list starts after the parameter specification and begins with a colon and precedes the function body. Initialization lists are essential for types for which assigment does not work, that is for member objects of classes without default constructors,for const members and for reference members.

Often it is usefull to specify default values for the parameters which should be used if no parameter value is supplied.

The instantiated objects occupy memory different from the class where the member functions are stored. Each non-static member function maintains a pointer, named “this”, which points to the object that is calling it. The expression *this refers to the object for which a member function is invoked. Most use of this is implicit.

Constructors are called when an object comes to live, destructors when it is destroyed. Destructors are called implicitly when an automatic variable goes out of scope, an object on the free store is deleted, etc. Only in very unusual circumstances does the user need to call a destructor explicitly. The most common use of a destructor is to release memory acquired in a constructor.

If a class has class objects as members then the member objects are constructed first, based on the initialization list, in the order of declaration. When the class is destroyed the objects own destructor is executed first and then the members destructors in reverse order of declaration.

In a class only static integral constant members can be initialized.


// definition of a class with constructor, initialization list and default parameters
class Ratio
{    public:
Ratio(int n=0,int d=1) : num(n),den(d) {reduce();}        // constructor with default values and initialization list
Ratio(const Ratio& r): num(r.num),den(r.den) {}           // copy constructor
private:
void reduce();
int num,den;
};
void Ratio:reduce() { ... }

int main()
{
Ratio x(4),y(x);
}


Every class has default two constructors, a copy assignment operator, and a destructor which are automatically created:
• Default constructor: X();
• Copy constructor: X(const X&);
• Assignment operator: X& operator=(const X&);
• Destructor: ~X();
If either of these are not defined explicitly, then it is automatically defined implicitly by the system. Note that the copy constructor takes one parameter: the object that it is going to copy. That object is passed by constant reference because it should not be changed. The copy constructor and assignment operator copy the complete state of an existing object into a new object of the same class. The copy constructor is called automatically whenever:
• an object initializated with a copy
• an object is passed by value to a function
• an object is returned by value from a function

You only need to define a copy constructor and assignment operator explicitly if a memberwise copy is not what you need. This is normally the case if member objects are pointing to data. In that case the memberwise copy can result in disastrous behavior. Below is an example that deals with this situation. The reason why the assignment operator returns a reference to an object, is to allow chained calls for the operator. Essentially x=y=z=4; is shorthanded for x.operator=(y.operator=(z.operator=(4)));

A constructor with one argument should normally be defined with the keyword explicit. This avoids that the compiler unintentionally constructs an object with an assignment operator. So if s is a string object, with implicit construction the compiler translates s=10 into s("10") instead of creating an empty string of 10 positions. This is unnoticed for the programmer at compile time and should be avoided.


// definition of a class that allocates memory
class Name {
const char* s;
//..
};
class Table {
Name* p;
size_t sz;
public:
Table(size_t s=15) {p = new Name[sz=s];}    // constructor
~Table() {delete[] p;}                      // destructor
Table(const Table&);                        // copy constructor
Table& operator=(const Table&);             // copy assignment
};
Table::Table(const Table& t) {
p = new Name[sz=t.sz];
for(int i=0;i<sz;i++) p[i]=t.p[i];
}
Table::Table& operator=(const Table&) {
if(this!=&t) { //avoid self-assignment
delete[] p;
p= new Name[sz=t.sz];
for(int i=0;i<sz;i++) p[i]=t.p[i];
}
return *this;
}



#### Static members

Static members are part of a class, but not part of an object of that class. There is exactly one copy of a static member. Also a function that need access to members of a class, but does not need to be invoked for a particular object is called a static member function. Because static member functions are not attached to an object, they have no this pointer. Static member functions do not work on an object, so the this pointer is not needed. Second, static member functions can only access static member variables. They can not access non-static member variables. This is because non-static member variables must belong to a class object, and static member functions have no class object to work with.


// declaration of a static member function: num() and a static member data: count
class Widget {
public:
Widget() { ++count; }
~Widget() { --count; }
static int num() { return count; }
private:
static int count;
};
int Widget::count = 0;
int main() {
Widget x,y,z;
cout << Widget::num();
}



#### Constant member functions

Like variables and function parameters also member functions can be defined const: T f() const{};A const member function does not modify the state of an object. Also objects may also be declared to be constant. A const member function can be invoked for both const and non-const objects, whereas a non-const member function can be invoked only for non-const objects.

#### Pointers to class objects


// (*p).data <=> p->data
class X {
public:
int data;
};
int main() {
X* p = new X;
(*p).data = 22;  		// . has higher precedence than * therefore parentheses required
p->data = 22;               // same meaning, but prefered reference method
cout <<  p->data << endl;
}



C++ includes a rich store of 45 operators. These operators are defined automatically for the fundamental types (int, float, etc.). When you define a class, you are actually creating a new type. Most of the C++ operators can be overloaded to apply to your new class type. There are binary and unary operators. A binary operator can be defined by either a nonstatic member function taking one argument or a nonmember function taking two arguments. For example:


class X {
public:
void operator+(int);
X(int);
};
void operator+(X,X);
void operator+(X,double);

void f(X a) {
a+1;        //a.operator+(1)
1+a;        //::operator(X(1),a)
a+1.0;        //::operator(a,1.0)
}


An unary operator, prefix or postfix, can be defined by either a nonstatic member function taking no arguments or a nonmember function taking one argument. @aa can be interpreted as aa.operator@() or operator@(aa). If both are defined, overload resolution determines which interpretation is used.


T& T::operator=(const T& t)
{ // assign each member datum of t to the
// corresponding member datum of the owner
return *this;
}



### Functors

Functors (also called function objects or functionoids) are one of the most powerful features of the C++ language, especially in conjunction with STL algorithms. In C++, to create a functor, you create a class that overloads the parentheses operator, operator ( ).


class Convert
{
public:
explicit Convert(const double factor): _factor(factor) {}
double operator() (const double amount)
{
return amount*_factor;
}
private:
double _factor;
};

Now with this functor we can easily use the advantage to store a conversion factor between multiple function calls.

main()
{
Convert meters_to_miles(0.000621371192);
double distance_in_meters=1200;
double distance_in_miles=meters_to_miles(1200);
}


### Enum types

In C and C++, enum types can be used to set up collections of named integer constants. (The keyword enum is short for enumerated.)


#define SPRING   0
#define SUMMER   1
#define FALL     2
#define WINTER   3


An alternate approach using enum would be


enum { SPRING, SUMMER, FALL, WINTER };


If you don't specify values for enum constants, the values start at zero and increase by one with each move down the list. If you want, you may provide explicit values for enum constants, as in


enum FooSize { SMALL = 10, MEDIUM = 100, LARGE = 1000 };


There are two kinds of enum type declarations. With and without a name. If you give an enum type a name, you can use that type for variables, function arguments and return values.


FooSize x=MEDIUM;


There is an implicit conversion from any enum type to int. But not the reverse


int i = SMALL; // i=10
FooSize x=10;  // error


## Libraries

Dynamic library files have some advantages over static library files: 1) can be used by multiple EXE files, 2) updates are easier 3) smaller sized EXE files. A

Visual Studion
Creating a library: specify the project type in the project - properties window:

Additional for a dynamic library one has to specify for each function which is exposed to be called by an external program the following specifier: __declspec(dllexport).

To use the library the linker must be able to find the library. For libraries where the source code is available one can add a project dependency to the project.

For other libraries you can use the drag-and drop method, drag the .lib file to your project solution window. So for dynamic libraries do not use the dll file.

or alternatively use the configuartion section of the project properties and specify the additional dependencies:

For dynamic libraries the include header file should contain the following specifier __declspec(dllimport) for each imported function from the library. A reuable header file could have following form:

To define your exports, you must go to Project->Properties->C/C++->Command Line and add the flag /D. This stands for define. In this specific case, you are defining BUILD_DLL, which means you intend to implement this library as an export. Users of the library would not be defining the variable if they intended to use the library.

CRT Libraries
The CRT in a nutshell is all the library functions you rely on to develop your code. It includes the Standard C++ Library as well as the Microsoft functions and declarations. This is a summary list of the libraries you can integrate with. For the full list, see MSDN.

• LIBCPMT.LIB - Multithreaded (Standard C++ Library) /MT
• LIBCMT.LIB - Multithreaded (C Runtime Library) /MT
• MSVCPRT.LIB - Multithreaded Dynamically Linked Library w/ MSVCP90.dll (Standard C++ Library) /MD
• MSVCRT.LIB - Multithreaded Dynamically Linked (C Runtime Library) w/ MSVCR90.dll /MD
To set your version of the CRT, go to 'Project Properties->Code Generation->Runtime Library' and select either /MT, /MTd, /MD, or /MDd, (Multithreaded[debug] or Multithreaded DLL[debug]). "If you design your DLL so that it passes CRT objects across the boundary or allocates memory and expects it to be freed outside the DLL, you restrict the DLL users to use the same copy of the CRT library as the DLL. The DLL and its users use the same copy of the CRT library only if both are linked with the same version of the CRT DLL." The version of CRT used for compiling the library can be found with following command line command:
 dumpbin /imports

See MSDN.