Absolute C++心得(续1)

来源:互联网 发布:游戏编程基础 编辑:程序博客网 时间:2024/04/29 11:01
11、在重载操作符时,该操作符所包含的参数必须至少有一个是类类型。
重载操作时不能更改操作符所包含的参数个数。即不能把二元操作符重载成一元操作符。
操作符重载不会改变操作符的优先级。重载后的操作符和重载之前拥有相同的优先级。
重载的操作符不能包含默认参数。
=、[]、->和()只能作为类的(非静态)成员函数重载。

点操作符(.)、作用域说明符(::)、sizeof、三元操作符(?:)及(.*)不能被重载。

12、当定义一个成员函数或者成员操作符时,可以直接访问调用对象的私有成员亦是(或私有成员函数)。然而,不仅仅如此,我们还可以直接
访问该类任何对象的任何私有成员变量(或私有成员函数)。(见第29条)

13、作为友元的操作符或者函数必须在类的定义中列出其声明,就像在类中列出成员函数的声明一样,区别在于必须在函数声明前面加上关键字
friend。但是友元不是成员函数,不能在函数的定义的第一行中加上类修饰词。

14、不能对类类型的成员变量返回引用。只能返回常量类型。否则可以修改私有的成员变量,因为引用类型可以做为左值使用。

15、假设返回值的类型为T,那么一个函数的返回值有以下4种不同的方式:
1)返回一般的值,对应的函数声明为 T f();
这种返回值类型不能作为左值,而且返回值可以直接调用成员函数来修改,即使用f().mutator()。返回值可以调用复制构造函数。
2)返回常量值,对应的函数声明为const T f();
上1)相似,唯一不同在于返回值不能直接调用成员函数来修改,即不能使用f().mutator()。
3)返回引用,对应的函数声明为 T& f();
这种返回值类型可以作为左值,而且返回值可以直接调用成员函数来修改,即使用f().mutator()。返回值可以调用复制构造函数。
4)返回常量引用,对应的函数声明为const T& f();
这种返回值不能作为左值,而且返回值不能直接调用成员函数来修改,即不能使用f().mutator()。返回值不能调用复制构造函数。
何时采用某种返回值类并没有明确统一的规定。
如果返回值类型是简单的数据类型,如int或char,那么在返回值时使用与不使用const修饰没有实际的意思。
如果希望简单数据类型的返回值可以作为左值,即可以放在赋值操作符的左边,那么就必须返回引用类型;反之,就返回一般值。
对于返回值为类类型的情况,是否返回引用类型取决于返回的对象是否可以作为左值。如果希望返回对象作为左值,那么就返回
引用类型。返回一个局部变量的引用,不论是否使用了const修饰词,都会产生问题。

16、重载前置++和后置++,形式应该如下:
class operator ++();//前置
class operator ++(int ignoreMe);//后置

17、char shortString[] = "abc";
        char shortString[] = {'a','b','c'};
这两种字符串数组初始化是不同的。第一种方式在字符'a','b','c'后面添加空字符串'\0';而第二种初始化则不会添加'\0'。

18、复制构造函数是包含一个引用调用参数的构造函数,而且该引用调用参数的类型和该类类型相同。复制构造函数的参数必须
是引用调用参数,而且通常也是一个常量参数(即使用const修饰词修饰)。
当C++需要产生一个对象的副本时,就会自动调用复制构造函数。尤其,在下面3种情况下,复制构造函数都会自动被调用。
1)当声明一个类的对象时,使用另外一个对象来初始化。例如 classA(const classA& variable)。
2)当一个函数返回值为类类型时。
3)当一个类类型的实参传递给函数中的传值调用参数时。例如:
class classA
{
classA(const classA& other);
classA(int size);
void addElement(int a);
private:
int *a;
int size;
}
void show(classA parameter)
{
cout << "the first value is" <<parameter[0] <<endl;
//如果类classA没有复制构造函数,而是用系统简单的复制构造函数,当该函数调用执行时,sample的值被复制到局部变量
//parameter,因此parameter.a就等于sample.a。当该函数调用执行结束后,会调用析构函数,释放parameter所占用的空间
//即释放parameter.a,相当于sample.a被释放了。会导致问题!!!!
}
调用如下:
classA sample(2);
sample.addElement(5.5);
sample.addElement(6.6);
show(sample);
cout << "after call" << sample[0] << endl;

19、C++不允许一个类被多次定义,哪怕这些重复的定义是完全相同的。如果在许多不同的工程中使用相同的头文件,想要知道是否
在一个文件中多次包含了某个类的定义机会是不可能。因此用如下方式:假设在头文件test.h定义类Test
#ifndef TEST_H
#define TEST_H
<类的定义>
#endif

20、未命名的名字空间中定义的名字都局限于该编码单元中。例如在文件test.cpp
namespace
{
void func();
}
namespace test
{
//在该命名空间中可以直接使用func(),而在文件test.cpp之外就不可以使用func()。
}

原创粉丝点击