Reliable Software Logo

C++ In Action: Language

Types

Built in types, typedefs.

Here is the list of built-in types with a short description of each of them.

  • bool-Boolean type. Can take predefined values true and false.
  • int -generic signed integral type. Its size is machine dependent, it is considered the most efficient implementation of an integral type for a given architecture. At least 2 bytes long.
  • double - generic signed floating point type.
  • char -generic 8-bit character type. Used in ASCII strings. Depending on the compiler, the default signedness of char may be signed or unsigned.
  • short and long are a little better defined signed integral types. Usually short is 2-byte long and long is 4-byte long, but on a 64-bit machine it may be 8-bytes long (same as int). If you are writing your program to be run on only one type of processor architectures, you may make assumptions about the sizes of shorts and longs (and chars, of course). Sizes become crucial when you start storing data on removable disks or move them across the network.
    Short is often used as a cheap int, space-wise; for example, in large arrays. Long is often used when short or int may overflow. Remember, in two bytes you can store numbers between -32767 and 32767. Your arithmetic can easily overflow such storage, and the values will wrap around.
  • float is a cheaper version of double (again, space-wise), but it offers less precision. It makes sense to use it in large arrays, where size really matters.
  • Additional floating point type of even larger size and precision is called long double.
  • All integral types may be prefixed by the keyword unsigned or signed (default for all types--except, as mentioned above, char--is signed). Of unsigned types, of special interest is unsigned char corresponding to a machine byte, and unsigned long often used for low-level bit-wise operations.

When you are tired of typing unsigned long over and over again, C++ lets you define a shortcut called a typedef. It is a way of giving a different name to any type--built-in or user defined. For instance, an unsigned long is often typedef'd to (given the name of) ULONG:

typedef unsigned long ULONG;

After you define such a typedef, you can use ULONG anywhere you would use any other type, for example,

ULONG ValueHolder::SwapValue (ULONG newValue)
{
    ULONG oldValue = _ulNumber;
    _ulNumber = newValue;
    return oldValue;
}

Similarly one often uses typedefs for BYTE

typedef unsigned char BYTE;

Like every feature of C++, typedefs can be abused. Just because you can redefine all types using your own names, doesn't mean you should. What do you make of types like INT or LONG when you see them in somebody else's code? Are these typedef'd names for int or long? If so, why not use directly int or long? And if not, then what the heck is going on? I can't think of any rational reason to typedef such basic data types, other than following some kind of coding standard from hell.

Besides these basic types there is an infinite variety of derived types and user defined types. We've had a glimpse of derived types in an array of chars. And we've seen user-defined types called classes.


NextNext: Summary