The difference between C++ and C:
In C, constant values default to external linkage, so they can appear only in source files. In C++, constant values default to internallinkage, which allows them to appear in header files.
When you declare a variable as const in a C source code file, you do so as:
const int i = 2;
You can then use this variable in another module as follows:
extern const int i;
But to get the same behavior in C++, you must declare your const variable as:
extern const int i = 2;
For objects that are declared as const, you can only call constant member functions. You can call either constant or nonconstant member functions for a nonconstant object. You can also overload a member function using the const keyword; this allows a different version of the function to be called for constant and nonconstant objects.
Some tricks in c may seem unnecessary in C++.
Hint
Note
In C++, arrays can declare as const expression length.
关于使用指针和引用:使用指针和引用是为了能够不复制对象, 一般指针用于处理需要修改对象的情形,而引用一般使用常引用, 不会修改被引用的对象。不过这个规则对于类似与Java这样的没有指针的语言就不成立, 它对于对象都是引用。
Class hierarchies and abstract class 是两个不同的概念, 前者侧重于类的重用,后者侧重于多态性。综合两者,可以实现抽象工厂的设计模式。
Templates are a compile-time mechanism so that their use incurs no run-time overhead compared to “hand-written code”.
注意string类型的c_str()函数返回的是当前string的指针,有可能当前对象是一个临时对象, 所以尽量不要使用c_str()。
You don’t have to know every detail of C++ to write good programs.
A float point literal is of type double.
Note a enum’s range, and an enum type can’t be initialized out of range.
If no initializer is specified, a global, namespace, or local static object is initialized to 0, while local vairables and objects created on the free store are not initialized. The same rule applies to class, static member are initialized by default while for normal member, only class type member are initialized by default contructor, built in types are not initialized.
no “implicit int” rule in C++, which is different from C.
合法的名字:只能有数字,字母,下划线组成,只能由字母开头。
C和C++一样有块级作用域,只是不能在循环中声明变量罢了。
不能在函数中再去定义和参数同名的变量。
The initializer for a “plain” T& must be an lvalue of type T. But for rvalue, can use const reference, for example:
const int & ref = 0;
为了避免拷贝,可以把指针和引用作为函数参数,如果需要改变这个参数, 那么传指针,否则传常引用比较方便。
类型在被使用前必须先被声明,注意下面的代码:
struct List; //因为在定义Link时使用了List,先在这里声明
struct Link {
Link * next; //注意这里是指针,不用先声明,因为指针是integral value
List * member_of;
};
struct List {...};
注意 cin.putback(ch); 以及在C中的 ungetc.
四种cast:
Implicit type conversion may take place when arguments passing.
A void function can return a call of a void function.
Note
Function Overload
函数重载的处理方式:判断实际参数转换到这个重载函数的级别, 级别最低的函数被调用,如果两个函数级别最低,则会报错(编译型错误)。
转换等级为:
Functions declared in different non-space scopes do not overload. For example:
void f(int);
void g()
{
void f(double);
f(1); // call f(double)
}
通过 using 来引入其他namespace的功能:
using Lexer::get_token;
An inline function must be defined - by identical definitions - in every translation unit in which it is used. 如果在头文件中定义了 inline function那么,引用它的源文件都会获得一份同样的定义。 所以一般在头文中中定义内联函数。
By default, consts and typedefs have internal linkage.
什么应该放在源文件中:(知道这个也就知道什么应该被放在头文件中)
如果模块a要使用模块b的全局数据:
A function defined in the body of a class declaration is an inline function. If a function isn’t define in the body of a class declartion, it can be defined as inline explicitly.
class Test
{
public:
int a() { return 1; }
int b();
};
inline int Test::b()
{
return 2;
}
In the above example, both a and b are inline functions. Note: b can be declare as inline expilictly. inilne int b();
如果一个成员函数被声明为const,那么它不会改变当前对象的状态, 但这并不意味着它不能改变对象的属性,可以把这些属性声明为 mutable, 这样的场景在cache中很常见。
注意copy initialization 和 copy assignment:
Table t1;
Table t2 = t1; // copy initialization
Table t3;
t3 = t2; // copy assignment
构造和析构的顺序:
注意这个用法: X * p = new(buf) X;
注意模板是一种编译型的特性。模块会在编译时生成各种函数。 为了防止生成生成太多的代码,可以考虑对模板在对于指针类型时进行specification.
通过 template<> class Vector<void*> 进行specification, 然后可以通过 template <class T> class Vector<T*>: private Vector<void*> 让它对于所有的pointer都成立,注意它和直接定义 template<class T> class Vector<T*> 的区别。