|< C++ File I/O 2 | Main | C/C++ Exception Handling - try, catch, throw >| Site Index | Download |


 

 

 

 

 

MODULE 20

C AND C++ STORAGE CLASSES

const, volatile, local and global

 

 

 

 

 

My Training Period:  xx hours

 

The source code for this tutorial is available in C/C++ Storage class source codes.

 

The C++ storage classes programming abilities:

 

 

20.1  An Introduction

#include   <iostream>

// here, iostream, we have class declaration

// and implementation parts.  We may have member

// variables, member functions, array, pointers,

// struct, enum, typedef, normal variables etc.

#define ...

// other variables assigned to constant/symbolic constant

 

class MyClass

{ ... };

// class variables...

 

union

{...};

 

struct  struct1

{...};

// another variable...

 

enum enum1 {...};

// another variable...

 

inline int function1( )

{...}

// another variables here...

 

void function1();

{...}

// another variables here...

 

typedef R S;

// another variables here...

 

// other user defined data types...

 

int r, s, t;

 

main()

{

   struct X;

   enum Y;

   typedef P Q;

   union Z;

   class_type object1, object2;

   // class type variable or objects...

   ...

 

   int x, y;

   // other variables...

}

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

20.2    Storage Classes

  • Storage class specifiers tell compiler the duration and visibility of the variables or objects declared, as well as, where the variables or objects should be stored.

  • In C++ program we have multiple files.  In these files we may have normal variables, array, functions, structures, unions, classes etc.  So, variables and objects declared must have the visibility, the lifetime and the storage, when values assigned.

  • In C/C++ there are 4 different storage classes available: automatic, external, static and register.  It is similar in C explained somewhere in tenouk.com.

Storage class

Keyword

Automatic

auto

External

extern

Static

static

Register

register

 

Table 20.1: storage classes

  • The general form for declaring a storage class is:

storage_class   declarator;

  • For example:

extern   int  value;

auto long p = 5;

auto int q;

static int x;

 

20.2.1  Automatic Variable - auto

  • Local variables are variables declared within a function or blocks (after the opening brace, { of the block).  Local variables are automatic by default.  This means that they come to existence when the function in which it is declared is invoked and disappears when the function ends.

  • Automatic variables are declared by using the keyword auto.  But since the variables declared in functions are automatic by default, this keyword may be dropped in the declaration as you found in many source codes.

  • The same variable names may be declared and used in different functions, but they are only known in the functions in which they are declared.  This means, there is no confusion even if the same variables names are declared and used in different functions.

  • Examples if we want explicitly declare the automatic type:

auto   int  x, y, z = 30;

auto   char firstname;

  • Same as:

int   x, y, z = 30;

char  firstname;

 

20.2.2  External Variable - extern

  • External variables are variables that are recognized globally, rather than locally.  In other words, once declared, the variable can be used in any line of codes throughout the rest of the program.

  • A variable defined outside a function is external.  An external variable can also be declared within the function that uses it by using the keyword extern hence it can be accessed by other code in other files.  The following program segment example shows the intern keyword:

int    value1;

char   name;

double value2;

// three externally defined variables

 

void main()

{

       extern int value1;

       extern char name;

       extern double value2;

       // three externally defined variables can be accessed from outside of this main()

       extern value3;

       // can be accessed from outside of this main()

       ...

}

20.2.3  Static Variable - static

// demonstrates the static variable...

#include   <iostream>

using namespace std;

 

int funcstatic(int)

{

       // local variable should exist locally...

       int sum = 0;

       sum = sum + 10;

       return sum;

}

 

int main()

{

       int r = 5, s;

 

       // test the function calls several times...

       cout<<"Without static keyword\n";

       cout<<"----------------------\n\n";

       s = funcstatic(r);

       cout<<"1st time function call, s = "<<s<<endl;

       s = funcstatic(r);

       cout<<"2nd time function call, s = "<<s<<endl;

       s = funcstatic(r);

       cout<<"3rd time function call, s = "<<s<<endl;

       return 0;

}

 

Output:

 

C++ storage class static keyword

int sum = 0;

static int sum = 0;

C++ storage class static keyword effect

 

20.2.4  Register Variable - register

20.2.5  Global Variables

20.2.6  Local Variables

extern int global1;

 

// object.h file, the header file

// extern global variable, external to object.cpp

extern int global1;

 

// class declaration part

class object

{

  public:

      int   objectvar;

 

  public:

      object(void);

      int set(int);

      ~object(void);

};

// this header file cannot be compiled or run

// extern...

int global1 = 30;

int global2 = 40;

 

// the class implementation file

// object.cpp file

#include <iostream>

using namespace std;

#include  "object.h"

 

// extern...

int global1 = 30;

int global2 = 40;

 

// class implementation part

object::object(void)

{

      objectvar = 0;

}

 

int object::set(int newvalue)

{

      int local1 = 10;

      // non extern with same variables name....

      global1 = 60;

      global2 = 70;

     

      // display the local variable locally...

      cout<<"In object.cpp file, local function, local1 variable = "<<local1<<endl;

      // display the global variable locally...

      cout<<"In object.cpp file, global1 variable = "<<global1<<endl;

      cout<<"In object.cpp file, global2 variable = "<<global2<<endl;

      return  newvalue;

}

 

object::~object(void)

{

       objectvar = 0;

}

int object::set(int newvalue)

{...}

int local1 = 10;

// non extern, with same variables name....

global1 = 60;

global2 = 70;

object   FirstObject;

// external to object.cpp

extern int global2;

// local to this main() function...

int local2 = 20;

 

// mainobject.cpp file, here is the main program,

#include   <iostream>

using namespace std;

#include   "object.h"

 

void main()

{

   object   FirstObject;

   // external to object.cpp

   extern int global2;

   // local to this main() function...

   int local2 = 20;

 

   cout<<"In object.h, global1 is object.cpp external variable = "<<global1<<endl;

   cout<<"In mainobject.cpp, global2 is object.cpp external variable =  "<<global2<<endl;

   cout<<"In mainobject.cpp, object value =  "<<FirstObject.set(50)<<"\n";

   cout<<"In mainobject.cpp, local function, local2 variable = "<<local2<<endl;

}

 

Output:

 

C++ storage class local vs global variables

 

20.3  Constant Values - const

// a pointer to a constant int
int const *PtrVar;

	
// a pointer to a constant int
int const (*PtrVar);

	
// a constant pointer to an int
int *const PtrVar;

	
// a constant pointer to an int
int (*const PtrVar);

// const variable

#include <iostream>

using namespace std;

 

int main()

{

       // p = 10 is a constant value, cannot be modified

       // during the program execution...

       const int p = 10;

       cout<<"q = p + 20 = "<<(p + 20)<<" where, p = 10"<<endl;

       // the following code should generate error, because

       // we try to modify the constant value...

       // uncomment, recompile notice the error...

      

       // p = 15;

       // --p;

       return 0;

}

 

Output:

 

C++ storage class const keyword program example

// const variable

#include <iostream>

using namespace std;

 

const int ArrayOne = 64;

// the following code is legal in C++, but not in C

char StoreChar[ArrayOne];

 

int main()

{

    return 0;

}

// no output for this example

// a const pointer to a variable...

#include <iostream>

using namespace std;

 

int main()

{

       // declare the pointers and let they point to something...

       // non const pointer...

       char *BuffOne = NULL, *BuffTwo = NULL;

       // a constant pointer...

       // assign the BuffOne pointer to PtrOne pointer

       char *const PtrOne = BuffOne;

      

       // let it point to some data...

       *PtrOne = 'z';

       cout<<"The value pointed by constant pointer is "<<*PtrOne<<endl;

      

       // the following code will generate error, because we try to

       // assign non const pointer to const pointer...

       // PtrOne = BuffTwo;

      

       return 0;

}

 

Output:

 

C++ storage class const keyword program example

Error:  project.cpp(17, 10):Cannot modify a const object

 

// a pointer to a const variable...

#include <iostream>

using namespace std;

 

int main()

{

       const char *BuffOne = "Testing";

      

       cout<<"The data pointed by BuffTwo is "<<BuffOne<<endl;

      

       // the const pointer BuffOne assigned to the

       // const pointer ThePtr is OK...

       const char *ThePtr = BuffOne;

       cout<<"The data pointed by ThePtr is "<<ThePtr<<endl;

      

       // the following code will generate an error

       // cannot modify the const

       // *ThePtr = 'z';

      

       return 0;

}

 

Output:

 

C++ storage class const keyword manipulation

 

  • Uncomment the code // *ThePtr = 'z'; and re-compile the program, the same error as in the previous example should be expected.

  • The const declaration also normally used in the definition of a function’s arguments, to indicate it would not change them as shown below making the code clearer and to avoid error.

int strlen(const char [ ]);

 

20.3.1  Constant Member Function

  • When declaring a member function with the const keyword, this specifies that it is a read only function that does not modify the object (notice the differences between variable versus object) for which it is called.

  • A constant member function cannot modify any data members or call any member functions that are not constant.

  • Implicitly, the const has set the ‘can’t modify’ *this pointer.  This can be changed by using the mutable (preferred) or const_cast operator.

  • Pointer to constant data can be used as function parameters to prevent the function from modifying a parameter passed through a pointer.

  • Place the const keyword after the closing parenthesis of the argument list.

  • const keyword is required in both the declaration and the definition.

  • A program example:

 

// constant member function

#include <iostream>

using namespace std;

 

// a class declaration part

class Date

{

   int  month;

   public:

       // we would test the month only...

       Date (int mnt, int dy, int yr);

       // a write function, so can't be const

       void  SetMonth(int mnt);

       // a read only function declaration

       int   GetMonth() const;

};

 

// a class implementation part

Date::Date(int,int,int)

{ //... }

 

void  Date::SetMonth(int mnt)

{

       // modify the non const member variable data

       month = mnt;

}

 

// a read only function implementation

int  Date::GetMonth() const

{

   // does not modify anything

   return  month;

}

 

// the main program

void main()

{

      Date    TheDate(7,4,2004);

      // non const member function, OK

      TheDate.SetMonth(11);

      cout<<"Month of the sample date is "<<TheDate.GetMonth()<<endl;

      // another dummy const object...

      const Date BirthDate(7,4,1971);

      // then try to modify the const object, NOT OK

      // BirthDate.SetMonth(5);

      // const member function sending message...

      BirthDate.GetMonth();

      // so, the following shouldn’t have the output data...

      cout<<"Another silly call, the month is "<<BirthDate.GetMonth()<<endl;

}

 

Output:

 

C++ storage class const member function source code example

Non-const function Date::SetMonth(int) called for const object

20.4  volatile

▪     Declaring volatile variable.  For example, volatile integer.

volatile int Vint;

int volatile Vint;

▪     Declaring pointers to volatile variables.  For example, pointer to volatile integer.

volatile int * Vintptr;

int volatile * Vintptr;

▪     Declaring volatile pointer to non volatile variables.  For example, volatile pointer to integer.

int * volatile Vptr;

▪     Declaring volatile pointer to a volatile variable.  For example volatile pointer to volatile integer.

int volatile * volatile Vptr;

▪     Using typedef example.

typedef volatile int Vint

▪     Illegal declaring after the first comma in multiple variable declaration example.

int p, volatile Vint;

20.5  Linkage

  1. External linkage,

  2. Internal linkage, or

  3. No linkage.

  1. If the declaration of an object or function identifier contains the storage class specifier extern, the identifier has the same linkage as any visible declaration of the identifier with file scope. If there is no such visible declaration, the identifier has external linkage.

  2. If an object identifier with file scope is declared without a storage class specifier, the identifier has external linkage.

  1. Any object or file identifier having file scope will have internal linkage if its declaration contains the storage class specifier static.

  2. For C++, if the same identifier appears with both internal and external linkage within the same file, the identifier will have external linkage. In C, it will have internal linkage.

  3. If a function is declared without a storage class specifier, its linkage is determined as if the storage class specifier extern had been used.

  1. Any identifier declared to be other than an object or a function (for example, a typedef identifier).

  2. Function parameters.

  3. Block scope identifiers for objects declared without the storage class specifier extern.

// demonstrates the static variable...

#include <iostream>

using namespace std;

 

int funcstatic(int)

{

     // local variable should exist locally...

     static int sum = 0;

     sum = sum + 10;

     return sum;

}

 

int main()

{

     int r = 5, s;

 

     // test the function calls several times...

     cout<<"Without static keyword\n";

     cout<<"----------------------\n\n";

     s = funcstatic(r);

     cout<<"1st time function call, s = "<<s<<endl;

     s = funcstatic(r);

     cout<<"2nd time function call, s = "<<s<<endl;

     s = funcstatic(r);

     cout<<"3rd time function call, s = "<<s<<endl;

     return 0;

}

 

Output:

 

C++ storage class program example using Visual C++ .NET

 

tenouk fundamental of C++ storage classes tutorial

 

 

 

 

 

 

 

 

 

 

 

 

Further C++ storage classes reading:

 

  1. Visual C++ .NET programming tutorials.

  2. The source code for this tutorial is available in C/C++ Storage class source codes.

  3. Check the best selling C / C++, Object Oriented and pattern analysis books at Amazon.com.

  4. Find a lot of information about C++ history and evolution at Bjarne Stroustrup site.

 

 

 

 

 

 

|< C++ File I/O 2 | Main | C/C++ Exception Handling - try, catch, throw >| Site Index | Download |