C++ Language Overview
Why C++?
- C++ is "C plus objects" (plus a whole lot more)
- C is a more specialized language for lower-level networking, operarating system, device code
- C++ is for bread-and-butter software that you want to run fast
- All features of C are accessible from C++, usually identically but sometimes slightly differently
- Primitive data types, representations, operators and control structures are identical in C and C++
- C++ has a much better library collection, in particular the Standard Template Library; see Containers in http://www.cplusplus.com/reference/ for reference
- C++ still is low-level compared to Java/Python/etc: must manually
freememory, array accesses and typecasts can be unsafe, need to be more concerned with memory layout, etc.
REFERENCE: We have a good book for learning C++, Accelerated C++. Click on the link for information and to download all of the code for the examples in the book.
C++ compiling
- name files
.cpp(preferred) or.cc - Header files are similar to C's and are still named
.h - use
g++ -std=c++11 -pedantic -Wall -Wextrato compile - (
g++is really just an option togccto let it know C++ code is coming) - All C tools work on C++ programs (
make,gdb,valgrind, etc)
Program Organization
- Functions and classes are used to organize code
- Independent functions can exist just like in C (or Python), no need to put them in a class like in Java
- Like C, executable programs must have a
mainfunction (not amainmethod in a class)
Pre-Processing
- All C libraries have a different name when used in C++ programs: put a
con front, leave off the.h - built-in math functions for example was
math.hin C, now:#include <cmath> - others:
<cstring> <cctype> <cstdlib>etc - C++ libraries have their own names:
<string>, <iostream>etc - eg:
#include <iostream> // C++ header file for i/o stuff
Namespaces
- C had a flat (global, single) namespace; not good for large amounts of code since name overlap could be a big problem
- C++ solution: explicit namespaces
- The libraries are defined in namespaces, and we need to clarify
where objects exist (name scope) even if we
#includethe relevant library. - The standard namespace,
std, is wherecout,string, and all other standard C++ library declarations live. - There are three ways to access entities declared in namespaces:
-
Qualify named entities with their namespace every time they are used:
std::cout << "hi there" << std::endl;wheremy_namespace::namerefers to unitnamedefined in namespacemy_namespace
(This is related to thejava.lang.*package hierarchy of Java but two levels only in C++.) - Put individual
usingdeclarations at the start of your file:using std::cout; using std::cin; using std::endl; using std::string;then refer to each unit without the namespace scope operation:cout << "hi there" << endl; - Claim you are using an entire namespace at the start of a file:
using namespace std;and likewise refer to each unit without the namespace scope:cout << "hi there" << endl;
WARNING: DON'T putusingstatements in your.hheader files, users of the header would get thoseusings and they may not want them!
-
Qualify named entities with their namespace every time they are used:
Pass by Reference
- Simple data types are passed by value in C++, as are object variables!
- Pointers (like in C) can be used to pass by reference
- NEW in C++: can use & to create a reference to a variable, another pass by reference option
- Think of
&in type as an 'alias' for a parameter - In method call just use variable name (not address of)
- Compiler implements by actually passing the address, and in effect puts "*" around all uses in body - similar to C pointer passing in behavior
- Can also use
&in local variable declarations, not just function parameters:int &d = c;createsdas alternate name for variablec - Fails to work in cases where the address-of/pointer approach in C would not work.
Example:int &d = 10;fails for the same reasonint *d = &10;fails -10has no address.
#include <iostream>
#include <string>
using namespace std;
void func(int value, int * pointer, int & alias) {
value = value + 1; // no effect on calling argument
*pointer = *pointer + 5; // changes calling argument
alias = alias + 10; // also changes calling argument
}
int main(void) {
int a = 10, b = 10, c = 10;
func(a, &b, c); // 2nd and 3rd parameters having same effect
cout << a << ' ' << b << ' ' << c << endl; // note explicit spaces
// prints 10 15 20
int &d = c; // d is now an reference to (alias for) c
d = 30; // changes c as well since they are aliases
cout << c << endl;
// prints 30
}