一道超经典且易错的笔试题

#include<iostream>

using namespace std;

class A

{

public:

A()  {    cout<<"A"<<endl;    }

~A() {    cout<<"~A"<<endl;   }

};

class B:public A

{

public :

B(A &a):_a(a)

{

cout<<"B"<<endl;

}

~B()

{

cout<<"~B"<<endl;

}

private:

A _a;

};

int main(void)

{

A a;       //很简单,定义a的时候调用了一次构造函数

B b(a);    //这里b里面的_a是通过成员初始化列表构造起来的

//而且是通过copy constructor构造的是b的成员对象_a的,这里是编译器默认的,因此在构造好_a前,先调用基类构造函数

//然后才是构造自身,顺序就是A()->_a->B()(局部)

//因此这里有两个A,一个B

//在return之前进行析构

/************************************************************************/

/*析构是按照定义对象的反顺序来的,而且同一个对象按照构造的反顺序来的,因此这里先

析构b然后才是a,那么b的构造顺序是上面的A()->_a->B()(局部),反过来,就是B()(局部)->_a->A()

因此得到的就是~B->~A->~A

在b之后就是析构a

最后结果就是

~B->~A->~A->~A*/

return 0;

}

此题的答案为:

A

A

B

~B

~A

~A

~A

仔细发现你可能会看出来多析构了一次A,其实在B b(a);  时,先调用了一次A构造函数,然后通过copy constructor构造b的成员对象_a(看清楚_a是一个A对象,并不是普通数据成员),由于没有显示声明A的默认拷贝构造函数,就默认调用编译器提供的默认拷贝构造函数。最后调用B的构造函数。

若将类A改成:

class A

{

public:

A()  {    cout<<"A"<<endl;    }

A(A &temp)

{

printf("A copy create!\n");

}

~A() {    cout<<"~A"<<endl;   }

};

那么结果为

A

A

A copy create!

B

~B

~A

~A

~A

时间: 2024-10-24 19:32:49

一道超经典且易错的笔试题的相关文章

一道极易出错的笔试题

#include <iostream> using namespace std; void func(int &x, int *x1) { x-=5;; x1+=10; } int main() { int a=100,b=200; func(b,&a); func(a,&b); cout<<a<<","<<b<<endl; } 题目看起来很简单,但很容易出错,此题的结果是 95,195 主要原来在x1

一道极易出错的笔试题2

#include<stdio.h> #include<string.h> int main() { char s[10]="love mm"; s[0]=0;//等价于 s[0]='\0';等价于s[0]=NULL; printf("%s\n",s); return 0; } 输出结果为: 结果是为空的,不明白的话接着看程序 #include<stdio.h> #include<string.h> int main()

10道C++输出易错笔试题收集(敢进来挑战吗?)

下面这些题目都是我之前准备笔试面试过程中积累的,大部分都是知名公司的笔试题,C++基础薄弱的很容易栽进去.我从中选了10道简单的题,C++初学者可以进来挑战下,C++大牛也可以作为娱乐玩下(比如下面的第6题).为了便于大家思考,将题目与答案分开,不过无论题目本身如何,我觉得后面的解析过程更值得学习,因为涉及很多我们学习C++过程中必知必会的小知识点 . 第一部分:题目 如下函数,在32 bit系统foo(2^31-3)的值是:() int foo(int x) { return x&-x; }

10道C++输出易错笔试题收集

下面这些题目都是我之前准备笔试面试过程中积累的,大部分都是知名公司的笔试题,C++基础薄弱的很容易栽进去.我从中选了10道简单的题,C++初学者可以进来挑战下,C++大牛也可以作为娱乐玩下(比如下面的第6题).为了便于大家思考,将题目与答案分开,不过无论题目本身如何,我觉得后面的解析过程更值得学习,因为涉及很多我们学习C++过程中必知必会的小知识点 . 第一部分:题目 如下函数,在32 bit系统foo(2^31-3)的值是:() int foo(int x) { return x&-x; }

[笔试题]sizeof系列面试题中的易错之处

sizeof系列笔试题看似简单,其实如果不深入探究,很容易出错,本人就有时败在了这,特写篇博客总结一番,引以为戒. V1.0 32位和64位编译器的区别 测试代码如下: #include "stdafx.h" #include <iostream> using namespace std; int main() { //32和64位编译器区别: 除了*与long随操作系统子长变化而变化外,其他的都固定不变(32位和64相比) //32: sizeof(*)=4 sizeof

C++经典笔试题详解

1.static有什么用途?(请至少说明两种) 1)在函数体,一个被声明为静态的变量在这一函数被调用过程中维持其值不变. 2) 在模块内(但在函数体外),一个被声明为静态的变量可以被模块内所用函数访问,但不能被模块外其它函数访问.它是一个本地的全局变量. 3) 在模块内,一个被声明为静态的函数只可被这一模块内的其它函数调用.那就是,这个函数被限制在声明它的模块的本地范围内使用 2.引用与指针有什么区别? 1) 引用必须被初始化,指针不必. 2) 引用初始化以后不能被改变,指针可以改变所指的对象.

Javascript易错知识点

? JS易错知识点总结: == 和 === 的区别: ==:判断两个变量的值是否相等. ===:判断两个变量的类型和值是否都相等,两个条件同时满足时,表达式为True. switch中break的作用: 如果一个case后面的语句,没有写break,那么程序会向下执行,而不会退出: 例如:当满足条件的case 2下面没有break时,case 3也会执行 1 var num = 2; 2 switch(num){ 3 case 1: 4 alert('case 1'); 5 break; 6 c

【转】嵌入式软件工程师经典笔试题

嵌入式软件工程师经典笔试题 > 预处理器(Preprocessor) 1. 用预处理指令#define 声明一个常数,用以表明1年中有多少秒(忽略闰年问题) #define SECONDS_PER_YEAR (60 * 60 * 24 * 365)UL 我在这想看到几件事情: 1). #define 语法的基本知识(例如:不能以分号结束,括号的使用,等等) 2). 懂得预处理器将为你计算常数表达式的值,因此,直接写出你是如何计算一年中 有多少秒而不是计算出实际的值,是更清晰而没有代价的. 3).

黑马程序员---C基础3【变量的易错】【程序结构】【if语句】【Switch语句】

------Java培训.Android培训.iOS培训..Net培训.期待与您交流! ------- [变量的易错] 1.变量为什么要初始化为0 int  sum,a=3: sum = sum+a 如果未初始化则会成为一个不确定的变量,结果也会不确定,容易出错. 2.不同类型的变量之间的转换 切记int  a=1,b=0:b=1-1.5:其中b为一个整型所有结果是保留整数部分的0,而不是-0.5,又因为0没有正负之分,所有保存结果为b=0: 3.关于Xcode的一个快速注释的插件 快捷键://