Core Knowledge Points in C++ Programming

Respect Function Interfaces and Minimize Internal Modifications

C++ Code Statements are divided into: built-in types, names, variables, operators, scalars, strings, preprocessor directives (such as #include), etc.Classes in C++ are defined to organize data structuresThe header files of the standard library are enclosed in angle brackets < >, while non-standard library header files are enclosed in double quotes ” “.Objects are regions in memory with a type.In C++, initialization and assignment are two different operations.Built-in type variables, if not initialized outside any function, will be initialized to 0 by the system; if not initialized within the function body, errors may occur (except when used as the left operand).Some class types have default constructors, so when defining their objects, explicit initialization may not be necessary. In C++, variables must be defined exactly once, and they must be defined or declared before use; declaring a variable does not allocate memory, so if declared without initialization, it is considered a declaration. If declared with initialization, it is considered a definition.extern keyword is used for declarations. Non-const variables defined in the global scope are by default extern. To allow const variables to be accessed in other files, they must be specified as extern.An important concept to understand is that references are just another name for an object, and initialization is the only way to specify which object a reference points to. For example, int val = 1024; int &refval = val; // refval is a reference to val; when int I = refval; it is equivalent to int I = val; A reference is a composite type.enum is the enumeration keyword enum Points{point2d, point2w, point3d, point3w}; it indicates that the members within the braces default to 0, 1, 2, 3, all of which are const variables. To initialize the value of an enumeration member, it must be a constant expression, but the initialization or assignment of an object of the enumeration type can only be done through its enumeration members or other objects of the same enumeration type. Points is an enumeration type.In C++, custom data types are defined by defining classes. A class defines the data contained in objects of that type and the operations that can be performed on objects of that type. Interface and implementation.There is a very important distinction between defining variables and defining data members; variables defined in a class are called data members. When defining data members, only the name and type of the data member can be specified. Data members are not initialized when defined in the class definition, but are controlled by a special member function called a constructor.In C++, the struct keyword can also be used to define classes, with the difference that members before the first access specifier in a struct are public by default, while in a class they are private by default. Note that private only refers to access permissions from outside the class; within the class, member functions can freely access private members.Header files are used for declarations rather than definitions, as definitions can only appear once, while header files can appear in multiple source files, so they are only used for declarations. There are three exceptions to the rule that header files should not contain definitions. Header files can define classes, const objects whose values are known at compile time, and inline functions. Header files contain class definitions and declarations of variables and functions needed for separate compilation.The C++ Preprocessor runs programs with preprocessor directives # before compilation, such as #include, which allows two forms <> and “”; the former indicates standard library header files, while the latter indicates custom header files. #define preprocessor variables are usually written in all uppercase letters. It can be used as follows:

#ifndef SALESITEM_H
#define SALESITEM_H // Definition of Sales_item class and related functions goes here
#endif

The first line checks if SALESITEM_H is defined; if not, the second line defines this preprocessor variable until #endif ends. If the first line finds that SALESITEM_H is already defined, it ignores the subsequent content. This preprocessor command can be used to prevent the internal definitions of classes in header files from being redefined when included multiple times, causing compilation errors.The input operator << for String type: ignores leading whitespace (spaces, tabs, newlines, etc.) and reads until the first occurrence of whitespace terminates the string. String literals contain an extra null character to terminate the string, so “string” contains 7 characters.First, get a rough understanding of the concepts of vector and iterator, and study them in depth when needed. The vector container is a type, and vector ivec represents a class template that holds int objects. An iterator is also a class, and vector::iterator iter; represents an iterator type object iter defined by vector, used to traverse elements in the container. They must be included in the file header and declared using using before use. Chapter 3 of C++ Primer introduces several commonly used standard library classes: vector, string, iterator, and bitset.C++ provides two low-level composite types similar to vector and iterator types—arrays and pointers. Modern C++ programs should prefer using vector and iterator types while avoiding low-level arrays and pointers. Well-designed programs should only use arrays and pointers internally in class implementations when emphasizing speed. Arrays can be defined with any built-in data type or class type, and array elements can be any composite type except references. The dimensions of an array must be defined using a constant expression with a value greater than or equal to 1. This constant expression can only contain integer literal constants, enumeration constants, or integer const objects initialized with constant expressions. Non-const variables and const variables whose values are only known at runtime cannot be used to define the dimensions of an array. Unlike vectors, arrays do not allow assignment and initialization with another array; once defined, arrays do not allow adding new elements.Pointers are defined as: int *p; read from right to left, defining p as a pointer variable pointing to an int type object. A valid pointer must be in one of the following three states: holding the address of an object; pointing to another object behind a certain object; or having a value of 0. Avoid using uninitialized pointers. Pointer arithmetic operations: adding or subtracting integer values. The arithmetic operations of pointers are implemented in the same way as iterators. Dereferencing a pointer gives the value of the object it points to: *p. When using an array name in an expression, it is actually using a pointer to the first element of that array, noting the equivalence of array names and pointer variables. C++ allows calculating addresses beyond the end of an array or object, but dereferencing that address is not allowed. For example:

const size_t arr_size = 5;
int arr[arr_size] = {0, 1, 2, 3, 4};
int *p = arr;
int *p2 = p + arr_size;

p2 holds the address beyond the end of the array arr_size.Pointer to const is understood as: “a pointer that thinks it points to const”; when a pointer is defined to point to a const object, it will consider itself as always pointing to a const object, even if it later points to a non-const object, it cannot modify the value of that object through dereferencing. However, it can modify the value by redefining a pointer that points to that object. In actual programs, pointers to const are often used as function parameters. There are also const pointers, such as int *const p = &val; const pointers restrict all modification behavior if they point to const objects.Bitwise Operators << and >> represent the overall left or right shift of binary digits by the number of bits specified by the right operand. For example, int 12 >> 1; indicates that 1100 becomes 0110 (6).Assignment operations return lvalues and have right associativity. The difference between j = i++ and j = ++i is that the former returns the initial value, while the latter returns the value after incrementing. Prefer using pre-increment. C++ provides a synonym for expressions containing the member access operator and dereference operator: -> arrow operator. For example: sales_item *sp = &item1; (*sp).same_isbn(item2); is equivalent to sp->same_isbn(item2);Using new and delete statements to create and release dynamic memory allows for the creation and release of dynamic arrays as well as single objects, such as: int *pi = new int; indicates that a single integer object is allocated in the free store (heap) and returns the address of that object, initializing pointer pi with that address. Similarly, int *pi = new int(20); initializes that integer object to 20. string *ps = new string; the default constructor of string initializes it to an empty string. To explicitly initialize a non-default initialized object, it can be written as: int *pi = new int(); adding parentheses after the type name indicates initialization to a null value, which can avoid errors caused by uninitialized values. delete pi; indicates releasing the memory pointed to by pi, but the address stored in pi still exists, making pi a dangled pointer, which can lead to errors; pi should be immediately set to 0 to indicate it no longer points to any object. Using delete to free memory not in the free store is illegal. For const objects, the address of the const object must be returned, such as: const int *pi = new const int(1024);C-style Strings are a const char type character array: const char *ps = “C style”; terminated by a null character; the C++ standard library redefines strings using the string type, which is simpler and more intuitive: string ps(“characters string”); prefer using the string class to define strings.The C++ compiler tries to prevent precision loss during implicit type conversion. The general format for explicit type conversion is: cast-name(expression); where cast-name is the type of conversion, such as static_cast; const_cast, etc., and type is the type to convert to. Avoid using explicit type conversion whenever possible.The switch statement requires a break after each case; otherwise, the program will only skip the subsequent case labels and continue executing the contents of the case label. If you want to define variables in a case, use braces to limit the scope of the variable.C++ Exception Handling keywords: throw and try{}catch{}catch{}…; understand that throw is used to exit a code block and transfer control to exception handling. try contains a block of code, and catch handles the corresponding statements.Using reference parameters in functions to modify the values of actual parameters is safe and convenient; avoid using pointers. If the function does not need to modify the value of the actual parameter, use const reference parameters uniformly, such as: the following program searches for character c in s:

string::size_type find_char(string &s, char c) {
    string::size_type i = 0;
    while (i != s.size() && s(i) != c) ++i;
    return i;
}

If this function is called find_char(“string”, ‘s’); a compilation error will occur, as string and character literals are rvalues; it can be referenced through const string &s, where the literal constant is implicitly converted to a temporary const object before initializing const string &s.Distinguish between int *matrix[10]; and int (*matrix)[10]; the former indicates an array of pointers containing 10 pointers, while the latter indicates a pointer to an array containing 10 int elements. The array subscript has higher precedence than the pointer operator. In int main(int argc, char *argv[]), argv is an array of C-style strings, char *argv[] is equivalent to char **argv, and argc holds the number of strings in argv.Lvalues can appear on both the left and right sides of an assignment statement, while rvalues can only appear on the right side of the assignment operator. Function return values are used to initialize temporary objects created at the call site. Therefore, functions can return references as lvalues: const string &shorterString(const string &s1, const string &s2), where both the parameter and return types are references. However, do not return references to local objects; similarly, pointers can be returned, but do not return pointers to local objects, as they will become dangling pointers.Recursive Functions are functions that call themselves directly or indirectly and must have a termination condition; otherwise, they will loop indefinitely. For example, defining a recursive function to calculate the value of 1×2×3…100:

int f(int val) {
    if (val > 1) return f(val - 1) * val;
    return val;
}

Function Declarations can omit parameter names, and default arguments are generally provided at the declaration stage: string screenInit(string::size_type width = 80, string::size_type height = 20, char background = ‘c’); when calling the function, the initialization values will overwrite the default argument values from left to right, so the most likely to change default arguments should be placed on the left. Function declarations are generally organized in header files, which are included in source files.In functions, each name has a scope, and each object has a lifetime; the lifetime of parameters and local variables is during the function call, and their name scope is limited to the function block from definition to the end of the block. If we want a local object to still have a lifetime after the function call ends, we can define a static local variable: static keyword. Defining inline functions is to allow the compiler to expand the statements in the function block when processing the function, saving the overhead of directly processing the function. The inline keyword is added before ordinary functions, and they can only be defined in header files.Member functions of a class can be declared within the class and defined outside the class or within the class. Their parameter list includes an implicit parameter this pointer, initialized to the address of the object that calls the member function, such as in the Sales_item class defined member function:

bool same_isbn(const Sales_item &rhs) const { return isbn == rhs.isbn;}

When calling total.same_isbn(trans), the const before the braces indicates that the implicit pointer this is a pointer of type const Sales_item* pointing to the total object; this function is called a constant member function. return isbn == rhs.isbn is equivalent to: return this->isbn == rhs.isbn; it is possible to explicitly use the latter statement in the function body, but it is unnecessary. A constructor is a special member function used to initialize a class, and constructors can be overloaded based on different numbers or types of parameter lists. Constructors have no return type and share the same name as the class.Typically, we define classes in header files named after the class, while member functions are defined in source files named after the class.Each version of a overloaded function should be declared in the same scope; locally named functions will override global functions rather than overload them.END

Source: https://www.sixstaredu.com/

Core Knowledge Points in C++ Programming

ShareCollectLikeView

Leave a Comment