目录
一、内存管理
二、运算符重载
三、this指针
四、构造&析构函数
五、模板
下面有关c++内存分配堆栈说法错误的是( )
A.对于栈来讲,是由编译器自动管理,无需我们手工控制;对于堆来说,释放工作由程序员控制
B. 对于栈来讲,生长方向是向下的,也就是向着内存地址减小的方向;对于堆来讲,它的生长方向是向上的,是向着内存地址增加的方向增长
C.对于堆来讲,频繁的 new/delete 势必会造成内存空间的不连续,从而造成大量的碎片,使程序效率降低。对于栈来讲,则不会存在这个问题
D.一般来讲在 32 位系统下,堆内存可以达到4G的空间,但是对于栈来讲,一般都是有一定的空间大小的
A.栈区主要存在局部变量和函数参数,其空间的管理由编译器自动完成,无需手动控制,堆区是自己申请的空间,在不需 要时需要手动释放
B.栈区先定义的变量放到栈底,地址高,后定义的变量放到栈顶,地址低,因此是向下生长的,堆区则相反
C.频繁的申请空间和释放空间,容易造成内存碎片,甚至内存泄漏,栈区由于是自动管理,不存在此问题
D.32位系统下,最大的访问内存空间为4G,所以不可能把所有的内存空间当做堆内存使用,故错误
C++中关于堆和栈的说法,哪个是错误的:( )
A.堆的大小仅受操作系统的限制,栈的大小一般较小
B.在堆上频繁的调用new/delete容易产生内存碎片,栈没有这个问题
C.堆和栈都可以静态分配
D.堆和栈都可以动态分配
- A.堆大小受限于操作系统,而栈空间一般有系统直接分配
- B.频繁的申请空间和释放空间,容易造成内存碎片,甚至内存泄漏,栈区由于是自动管理,不存在此问题
- C.堆无法静态分配,只能动态分配
- D.栈可以通过函数_alloca进行动态分配,不过注意,所分配空间不能通过free或delete进行释放
ClassA *pclassa=new ClassA[5];
delete pclassa;
c++语言中,类ClassA的构造函数和析构函数的执行次数分别为( )
A.5,1
B.1,1
C.5,5
D.程序可能崩溃
- A.申请对象数组,会调用构造函数5次,delete由于没有使用[],此时只会调用一次析构函数,但往往会引发程序崩溃
- B.构造函数会调用5次
- C.析构函数此时只会调用1次,要想完整释放数组空间,需要使用[]
- D.正确
使用 char* p = new char[100]申请一段内存,然后使用delete p释放,有什么问题?( )
A.会有内存泄露
B.不会有内存泄露,但不建议用
C.编译就会报错,必须使用delete []p
D.编译没问题,运行会直接崩溃
- A.对于内置类型,此时delete就相当于free,因此不会造成内存泄漏
- B.正确
- C.编译不会报错,建议针对数组释放使用delete[],如果是自定义类型,不使用方括号就会运行时错误
- D.对于内置类型,程序不会崩溃,但不建议这样使用
int globalVar = 1;
static int staticGlobalVar = 1;
void Test()
{
static int staticVar = 1;
int localVar = 1;
int num1[10] = {1, 2, 3, 4};
char char2[] = "abcd";
char* pChar3 = "abcd";
int* ptr1 = (int*)malloc(sizeof (int)*4);
int* ptr2 = (int*)calloc(4, sizeof(int));
int* ptr3 = (int*)realloc(ptr2, sizeof(int)*4);
free (ptr1);
free (ptr3);
}
1. 选择题:
选项: A.栈 B.堆 C.数据段(静态区) D.代码段(常量区)
globalVar在哪里?__C__ staticGlobalVar在哪里?__C__
staticVar在哪里?__C__ localVar在哪里?__A__
num1 在哪里?__A__
char2在哪里?__A__ *char2在哪里?__A__
pChar3在哪里?__A__ *pChar3在哪里?__D__
ptr1在哪里?__A__ *ptr1在哪里?__B__
分析:
char2是一个数组,把后面常量串拷贝过来到数组中,数组在栈上,所以*char2在栈上
pChar3局部变量在栈区 , *pChar3得到的是字符串常量字符在代码段
ptr1局部变量在栈区 ,*ptr1得到的是动态申请空间的数据在堆区
2. 填空题:
sizeof(num1) = __40__;//数组大小,10个整形数据一共40字节
sizeof(char2) = __5__;//包括\0的空间
strlen(char2) = __4__;//不包括\0的长度
sizeof(pChar3) = __4__;//pChar3为指针
strlen(pChar3) = __4__;//字符串“abcd”的长度,不包括\0的长度
sizeof(ptr1) = __4__;//ptr1是指针
下列关于赋值运算符“=”重载的叙述中,正确的是( )
A.赋值运算符只能作为类的成员函数重载
B.默认的赋值运算符实现了“深层复制”功能
C.重载的赋值运算符函数有两个本类对象作为形参
D.如果己经定义了复制拷贝构造函数,就不能重载赋值运算符
- A. 赋值运算符在类中不显式实现时,编译器会生成一份默认的,此时用户在类外再将赋值运算符重载为全局的,就和编译器生成的默认赋值运算符冲突了,故赋值运算符只能重载成成员函数
- B.默认的赋值运算符是按成员成员,属于浅赋值
- C.参数只有一个,另一个通过this指针传递
- D.两个函数的调用场景不同,相互没有影响
下列有关this指针使用方法的叙述正确的是( )
A.保证基类保护成员在子类中可以被访问
B.保证基类私有成员在子类中可以被访问
C.保证基类公有成员在子类中可以被访问
D.保证每个对象拥有自己的数据成员,但共享处理这些数据的代码
- A.基类保护成员在子类可以直接被访问,跟this无关
- B.基类私有成员在子类中不能被访问,跟this无关
- C.基类共有成员在子类和对象外都可以直接访问,跟this无关
- D.this指针代表了当前对象,能够区分每个对象的自身数据,故正确
下面描述错误的是( )
A.this指针是非静态成员函数的隐含形参.
B.每个非静态的成员函数都有一个this指针.
C.this指针是存在对象里面的.
D.this指针可以为空
- A.静态成员函数没有this指针,只有非静态成员函数才有,且为隐藏指针
- B.非静态成员函数的第一个参数就是隐藏的this指针
- C.this指针在非静态的成员函数里面,对象不存在,故错误
- D.单纯的对this赋空是不可以的,不过可以强转直接赋空,不过一般不进行这样的操作
在函数F中,本地变量a和b的构造函数和析构函数的调用顺序是: ( )
Class A;
Class B;
void F() {
A a;
B b;
}
A.b构造 a构造 a析构 b析构
B.a构造 a析构 b构造 b析构
C.b构造 a构造 b析构 a析构
D.a构造 b构造 b析构 a析构
- A.构造顺序是按照语句的顺序进行构造,析构是按照构造的相反顺序进行析构,因此先构造b错误
- B.a析构的时机不对,对象析构要在生存作用域结束的时候才进行析构,因此先析构a错误
- C.b的构造时机错误,先构造a
- D.正确,构造顺序是按照语句的顺序进行构造,析构是按照构造的相反顺序进行析构
设已经有A,B,C,D4个类的定义,程序中A,B,C,D析构函数调用顺序为?( )
C c;
int main()
{
A a;
B b;
static D d;
return 0;
}
A.D B A C
B.B A D C
C.C D B A
D.A B D C
- 类的析构函数调用一般按照构造函数调用的相反顺序进行调用,但是要注意static对象的存在, 因为static改变了对象的生存作用域,需要等待程序结束时才会析构释放对象
- 全局对象先于局部对象进行构造
- 局部对象按照出现的顺序进行构造,无论是否为static
- 所以构造的顺序为 c a b d
- 析构的顺序按照构造的相反顺序析构,只需注意static改变对象的生存作用域之后,会放在局部 对象之后进行析构
- 因此析构顺序为B A D C
拷贝构造函数的特点是( )
A.该函数名同类名,也是一种构造函数,该函数返回自身引用
B.该函数只有一个参数,是对某个对象的引用
C.每个类都必须有一个拷贝初始化构造函数,如果类中没有说明拷贝构造函数,则编译器系统会自动生成一个缺省拷贝构造函数,作为该类的保护成员
D.拷贝初始化构造函数的作用是将一个已知对象的数据成员值拷贝给正在创建的另一个同类的对象
- A.拷贝构造函数也是一构造函数,因此不能有返回值
- B.该函数参数是自身类型的对象的引用
- C.自动生成的缺省拷贝构造函数,作为该类的公有成员,否则无法进行默认的拷贝构造
- D.用对象初始化对象这是拷贝构造函数的使命,故正确
下面有关C++中为什么用模板类的原因,描述错误的是? ( )
A.可用来创建动态增长和减小的数据结构
B.它是类型无关的,因此具有很高的可复用性
C.它运行时检查数据类型,保证了类型安全
D.它是平台无关的,可移植性
- A.模板可以具有非类型参数,用于指定大小,可以根据指定的大小创建动态结构
- B.模板最重要的一点就是类型无关,提高了代码复用性
- C.模板运行时不检查数据类型,也不保证类型安全,相当于类型的宏替换,故错误
- D.只要支持模板语法,模板的代码就是可移植的
下列关于模板的说法正确的是( )
A.模板的实参在任何时候都可以省略
B.类模板与模板类所指的是同一概念
C.类模板的参数必须是虚拟类型的
D.类模板中的成员函数全是模板函数
- A.不一定,参数类型不同时有时需要显示指定类型参数
- B.类模板是一个类家族,模板类是通过类模板实例化的具体类
- C.C++中类模板的声明格式为template<模板形参表声明><类声明>,并且类模板的成员函数都是模板函数
- D.正确,定义时都必须通过完整的模板语法进行定义