面向对象编程(OOP)与面向过程编程的主要区别是?
规则:OOP 把「数据+操作」打包成对象;面向过程以函数/步骤为中心。
考点:OOP 基本思想。
解析:面向过程:先做什么再做什么(函数);面向对象:有哪些对象、各自有什么行为和属性。
排除法:OOP 也用函数(成员函数);用变量;不是不用函数。
面向对象中,一个「对象」由哪两部分组成?
规则:对象 = 属性(数据/成员变量)+ 行为(成员函数)。
考点:对象构成。
解析:如 Student 对象有 name/score(属性)和 show()(行为)。
排除法:缺一不可;类名/文件名无关。
「类(class)」与「对象(object)」的关系是?
规则:类是蓝图/模板,对象是按模板创建的具体实例。(GESP 考过「类是对象的实例」是错的)
考点:类与对象关系。
解析:class Student{...} 是类;Student a; 的 a 是对象(实例)。
排除法:方向反;不相同。
C++ 中 struct 和 class 的关系是?
规则:C++ 中 struct 也是类,唯一默认差异:struct 默认 public、class 默认 private。
考点:struct vs class(联网)。
解析:struct 可以有成员函数、构造、继承——只是默认访问级别不同。
排除法:struct 是类;可有成员函数。
class 中未写访问说明符的成员,默认访问级别是?
规则:class 默认 private;struct 默认 public。
考点:默认访问(联网)。
解析:class A { int x; }; 的 x 是 private,外部不可访问。
排除法:public 是 struct 默认;protected 是派生访问。
成员声明为 public,意味着?
规则:public = 类外部(对象、其他函数)可直接访问。
考点:访问控制。
解析:obj.publicMember 合法;private 成员外部访问编译报错。
排除法:private 才类内;protected 才派生。
把数据成员设为 private 的好处是?
规则:封装 = 数据私有 + 公有接口(getter/setter),保护数据不变量。
考点:封装。
解析:如 score 私有,只有 setScore 能改且可校验范围。
排除法:不更快/更短/省内存。
protected 成员可以被谁访问?
规则:protected:类内可访问,派生类可访问,类外不可。
考点:protected(联网)。
解析:介于 private(类内)与 public(全公开)之间,专为继承设计。
排除法:类外不可;不只友元。
构造函数(constructor)的作用是?
规则:构造函数在创建对象时自动调用,用于初始化。
考点:构造函数。
解析:Student a("Tom",90); 调构造函数给 name/score 赋值。
排除法:销毁是析构;复制是拷贝构造。
类没有定义任何构造函数时,编译器会?
规则:没定义任何构造 → 编译器自动生成无参默认构造。(GESP 考过)
考点:默认构造。
解析:class A{}; A a; 合法——a 用默认构造创建。
排除法:定义了带参构造后就不再自动生成默认构造。
类定义了带参构造函数(如 A(int x))后,还能 A a; 吗?
规则:定义了任何构造函数 → 编译器不再生成无参默认构造,A a; 报错。
考点:默认构造消失(联网)。
解析:class A{ public: A(int x){} }; A a; → 编译错误(无默认构造)。
排除法:这是常见坑;不自动生成。
析构函数(destructor)在什么时候调用?
规则:析构 ~类名() 在对象生命周期结束时自动调用。
考点:析构时机。
解析:局部对象离开作用域、delete 指针对象时调析构。
排除法:创建是构造;编译不调用。
成员函数中的 this 指的是?
规则:this 是指向当前对象的指针,成员函数内隐式可用。
考点:this。
解析:obj.f() 中 this=&obj;可用 this->m 访问成员。
排除法:指当前对象,非类/全局。
成员函数参数与成员同名时(如 void set(int score)),用 this 区分:this->score = score;。这是?
规则:形参 score 与成员 score 同名时,this->score 指成员,裸 score 指形参。
考点:this 区分同名。
解析:这是 this 最常见的用途之一;也可用初始化列表避免。
排除法:合法且常用。
对象指针 Student* p 访问成员用?普通对象 Student a 用?
规则:对象用 .,对象指针用 ->(等价于 (*p).m)。
考点:. vs ->(联网/GESP)。
解析:a.show();p->show()。
排除法:指针必须 ->;对象必须 .。
封装(encapsulation)通常的做法是?
规则:封装 = 数据私有化 + 提供公有接口访问。
考点:封装实现。
解析:getScore() 读、setScore() 写(可加校验)。
排除法:全 public 是反封装。
派生类继承基类的语法是?
规则:C++ 继承 class D : public B {};Java 是 extends。
考点:继承语法。
解析:D 继承 B 的成员;public 继承最常用。
排除法:extends 是 Java;其余语法错。
继承的主要好处是?
规则:继承 = 复用基类的属性和方法 + 派生类扩展/重写。
考点:继承意义(GESP 考过「继承是将已有类属性方法引入新类」)。
解析:Circle 继承 Shape,复用 area 接口并重写实现。
排除法:不必然更快/省内存。
多态(polymorphism)指的是?
规则:多态 = 基类指针/引用调虚函数时,运行时决定调哪个派生类的实现。
考点:多态。
解析:Shape* s = new Circle; s->area() 调 Circle 的 area。
排除法:非同名类/多对象。
C++ 实现多态,基类中需要把函数声明为?
规则:基类成员函数加 virtual 才支持多态(运行时按对象实际类型调)。
考点:虚函数。
解析:virtual double area() const 派生类 override。
排除法:static/inline/const 都不实现多态。
C++ 中重载 + 运算符(a + b)的写法是?
规则:重载运算符 = 定义 operator符号 成员(或友元)函数。
考点:运算符重载。
解析:Vec operator+(const Vec& o) const 使 a+b 合法。
排除法:宏不行;可重载大部分运算符。
构造函数初始化列表 A(int x): m(x) {} 的作用是?
规则:初始化列表在进入函数体前直接初始化成员(比函数内赋值更早)。
考点:初始化列表(联网)。
解析:m(x) 直接初始化;const/引用成员必须用初始化列表。
排除法:不是先默认再赋值。
explicit A(int x); 的作用是?
规则:explicit 阻止单参构造的隐式转换。
考点:explicit(联网)。
解析:A a = 1; 会隐式调 A(1);加 explicit 后必须 A a(1) 或 A a = A(1)。
排除法:防隐式转换,非加速/访问控制。
类含指针成员,默认拷贝构造函数做的是?
规则:默认拷贝 = 逐成员拷贝;指针成员只复制地址(浅拷贝),两对象指向同一内存。
考点:浅拷贝(联网)。
解析:Arr b = a; 后 b.p 与 a.p 同地址 → 各自析构时双 delete 崩溃。
排除法:深拷贝需自己写;默认就是浅拷贝。
需要「深拷贝」时(指针成员),做法是?
规则:深拷贝 = 自定义拷贝构造,为指针成员分配新内存并复制内容。
考点:深拷贝。
解析:Arr(const Arr& o): n(o.n), p(new int[o.n]) { copy(...); }。
排除法:默认不深拷贝。
面向对象编程的三大特性是?
规则:三大特性 = 封装(encapsulation)、继承(inheritance)、多态(polymorphism)。
考点:三大特性(GESP 考过)。
解析:GESP 2024 直接考「面向对象的编程思想主要包括哪些原则」。
排除法:递归/循环/指针不是 OOP 特性。
下列哪种语言不是面向对象程序设计语言?
规则:C 是过程式语言;C++/Java/Python 支持面向对象。
考点:OOP 语言(CSP-J 2021 考过)。
解析:C 没有 class/对象概念。
排除法:C++/Java/Python 都支持类。
运行下面代码,输出是?
01class Student { 02public: 03 string name; int score; 04 Student(string n, int s): name(n), score(s) {} 05 void show() { cout << name << ' ' << score; } 06}; 07int main(){ Student a("Tom",90); a.show(); }
规则:构造用初始化列表赋值,show() 输出 name 空格 score。
考点:基础类代码追踪。
解析:a 构造为 name="Tom"、score=90,show 输出 Tom 90。
排除法:顺序/空格是 show 里定的。
下面代码会怎样?
01class A { private: int x; }; 02int main(){ A a; a.x = 5; }
规则:class 默认 private,外部访问 a.x 编译报错。
考点:private 访问(GESP 考法)。
解析:x 未写访问说明符 → private → main 中不可访问。
排除法:编译期报错,非运行崩溃。
class B 中 x 声明在 public 区,B b; b.x = 5; 结果?
规则:public 成员外部可直接访问赋值。
考点:public 访问。
解析:class B { public: int x; }; 后 b.x=5 合法。
排除法:public 无访问限制。
运行下面代码,输出是?
01class C { 02 int n; 03public: 04 C(): n(0) {} 05 C& add(int x) { n += x; return *this; } 06 int get() { return n; } 07}; 08int main(){ C c; c.add(1).add(2).add(3); cout << c.get(); }
规则:add 返回 *this(引用自身),链式连续累加。
考点:this 链式。
解析:c.add(1)→n=1,返回 c;.add(2)→n=3;.add(3)→n=6。
排除法:链式都作用在同一对象 c。
运行下面代码,输出顺序是?
01class D { 02public: 03 D() { cout << "C"; } 04 ~D() { cout << "D"; } 05}; 06int main(){ D d; cout << "M"; }
规则:对象构造在 main 语句前,析构在 main 结束后。
考点:构造/析构时机。
解析:d 构造→输出 C;main 内输出 M;main 结束 d 析构→输出 D。CMD。
排除法:析构在作用域结束(main 后)。
下面代码,析构函数调用几次?
01class E { public: ~E() { cout << "~"; } }; 02int main(){ E a; { E b; } E c; }
规则:每个对象离开作用域析构一次;b 在块结束析构。
考点:析构次数。
解析:b 在 {} 结束即析构(1 次),a、c 在 main 结束析构(各 1 次),共 3 次。
排除法:块内对象提前析构。
下面代码会怎样?
01class F { public: int x; }; 02int main(){ F* p = new F; p->x = 5; cout << p->x; delete p; }
规则:new 创建堆对象、delete 释放;指针用 -> 访问。
考点:堆对象与 delete。
解析:p->x=5,输出 5,delete p 释放(配对无泄漏)。
排除法:忘记 delete 才泄漏。
类含 int* p(new 的数组),正确做法是?
规则:指针成员动态内存需在析构中 delete[] 释放(RAII)。
考点:RAII 析构。
解析:~Arr(){ delete[] p; },对象销毁时自动释放。
排除法:堆内存不会自动释放。
运行下面代码,输出是?
01class Shape { public: virtual double area() const { return 0; } }; 02class Circle : public Shape { 03 double r; 04public: 05 Circle(double x): r(x) {} 06 double area() const override { return 3.14 * r * r; } 07}; 08int main(){ Shape* s = new Circle(2); cout << s->area(); delete s; }
规则:虚函数 + 基类指针 → 运行时多态,调实际对象(Circle)的 area。
考点:多态代码追踪。
解析:s 指向 Circle(2),area()=3.14*4=12.56。
排除法:非虚函数才调基类版。
若上题 area 去掉 virtual,s->area() 输出?
规则:非虚函数按「指针静态类型」绑定(基类),不产生多态。
考点:虚函数必要性。
解析:无 virtual 时 s->area() 调 Shape::area → 0。
排除法:多态依赖 virtual。
运行下面代码,输出是?
01class Vec { public: int x,y; 02 Vec(int a,int b): x(a),y(b) {} 03 Vec operator+(const Vec& o) const { return Vec(x+o.x, y+o.y); } 04}; 05int main(){ Vec a(1,2), b(3,4); Vec c = a + b; cout << c.x << ',' << c.y; }
规则:operator+ 返回两向量分量和。
考点:运算符重载追踪。
解析:c = (1+3, 2+4) = (4,6)。
排除法:a+b 调 operator+。
成员是 const int c;,构造函数必须用?
规则:const/引用成员必须在初始化列表初始化(函数体内赋值非法)。
考点:初始化列表必须场景(联网)。
解析:const 成员不能在函数体赋值,必须 : c(v)。
排除法:函数体赋值 const 成员报错。
class A { public: explicit A(int x){} }; 下面哪个会编译错误?
规则:explicit 阻止 A a = 1 这种隐式构造。
考点:explicit(联网)。
解析:A a = 1 隐式调 A(1) → 被 explicit 阻止报错;A a(1) 显式合法。
排除法:显式调用不受影响。
含指针成员的类,Arr b = a;(默认拷贝构造)后 b.p 与 a.p?
规则:默认拷贝构造逐成员复制,指针成员复制地址 → 浅拷贝。
考点:浅拷贝。
解析:b.p == a.p,都指向同一块;任一析构 delete 后另一个悬垂。
排除法:深拷贝才新地址。
class G { public: static int count; }; static 成员 count 的特点是?
规则:static 成员属类所有对象共享,需类外定义一次。
考点:静态成员。
解析:G::count 全局一份,g1.count 与 g2.count 是同一个。
排除法:static 是共享非每对象。
int get() const { return n; } 中 const 的作用是?
规则:成员函数后 const = 承诺不修改对象(可被 const 对象调用)。
考点:const 成员函数。
解析:const C c; c.get() 合法;非 const 函数不能对 const 对象调用。
排除法:是只读承诺。
派生类对象创建时,构造执行顺序是?
规则:派生对象构造:先调基类构造,再调派生构造(析构相反)。
考点:继承构造顺序。
解析:Circle 创建 → 先 Shape() 再 Circle();销毁先 ~Circle 再 ~Shape。
排除法:基类先构造是 C++ 规则。
基类析构函数应声明为 virtual(virtual ~Shape(){}),因为?
规则:基类虚析构 → delete s(基类指针)会调派生类析构。
考点:虚析构(联网)。
解析:非虚析构时 delete Shape* 只调 ~Shape,派生资源(如 new 的成员)泄漏。
排除法:防泄漏,非速度。
Student a[3]; 要求 Student 类?
规则:对象数组需要默认构造(无参)逐个创建。
考点:对象数组。
解析:Student a[3] 依次调默认构造;类无默认构造(只有带参)则报错。
排除法:数组创建需要默认构造。
类外定义成员函数 void X::f() {},X:: 的作用是?
规则:X::f 表示 f 是类 X 的成员函数(类外定义)。
考点:类外定义(联网)。
解析:类内声明 void f();,类外 void X::f(){...} 实现。
排除法::: 是作用域限定符。
运行下面代码,说法正确的是?
01class Node { 02public: 03 int val; Node* next; 04 Node(int v, Node* n = nullptr): val(v), next(n) {} 05}; 06int main(){ Node a(1), b(2, &a); }
规则:构造默认参数 n=nullptr,只传一个参时 next 为 nullptr。
考点:构造默认参数(GESP 考法)。
解析:Node a(1) → val=1, next=nullptr;Node b(2,&a) → next=&a。
排除法:默认参数让单参调用合法。
下面代码,正确的是?
01class List { 02 struct Cell { int v; Cell* next; Cell(int x): v(x), next(nullptr) {} }; 03 Cell* head; 04public: 05 List(): head(nullptr) {} 06 void push(int x) { Cell* c = new Cell(x); c->next = head; head = c; } 07};
规则:push 新建节点、next 指向旧 head、head 更新 → 头插法。
考点:嵌套类 + 链表头插(GESP 考法)。
解析:c->next=head; head=c; 经典头插。
排除法:尾插需遍历到尾;嵌套类可访问。
关于 C++ 类的说法,错误的是?
规则:「类是对象的实例」错——应是「对象是类的实例」。(GESP 原题)
考点:类对象关系辨析。
解析:类是模板,对象是实例;方向反即错。
排除法:其余都正确。
关于构造函数,正确的是?
规则:没定义构造 → 编译器自动生成默认构造。(GESP 原题)
考点:默认构造(GESP)。
解析:class A{}; A a; 合法。
排除法:析构可省;定义构造后默认构造消失。
关于「定义了构造函数,创建对象时的执行顺序」,正确的是?
规则:定义了构造,创建对象只执行该构造;不存在「先默认再定义」。(GESP 原题判错)
考点:构造执行(GESP)。
解析:A(int x) 定义后,A a(1) 只调 A(int),不调别的。
排除法:没有双重构造。
把 score 设为 private 并提供 setScore(int s),好处是?
规则:封装让数据修改走接口,可加校验保证不变量。
考点:封装的价值。
解析:setScore(-5) 可被拦下(非法),直接 obj.score=-5 无法拦。
排除法:安全/可控是封装价值。
基类指针 delete 一个派生对象,若基类析构非 virtual,会发生?
规则:非虚析构时 delete 基类指针只调基类析构 → 派生类析构不执行 → 泄漏。
考点:虚析构必要性(联网)。
解析:delete s;(s 是 Shape*)若 ~Shape 非 virtual,不调 ~Circle。
排除法:泄漏是结果。
虚函数多态的底层机制是?
规则:含虚函数的类生成 vtable;对象首部存 vptr,调用虚函数时查表。
考点:vtable(联网)。
解析:s->area() 运行时查 s 指向对象的 vtable → 调 Circle::area。
排除法:多态是运行时查表,非编译期展开。
const C c; 对象能调用?
规则:const 对象只能调 const 成员函数(保证不修改)。
考点:const 对象。
解析:c.get()(get 是 const)合法;c.set(1)(非 const)报错。
排除法:const 对象限制调用非 const 函数。
static 数据成员(static int count;)必须?
规则:static 成员需类外定义(分配存储);类内只是声明。
考点:static 定义。
解析:int G::count = 0; 放在类外(全局),否则链接错误。
排除法:static 是类级,需类外定义。
成员是引用 int& ref;,必须用初始化列表,因为?
规则:引用成员必须在构造初始化列表绑定(引用无默认值,不能先构造后赋值)。
考点:引用成员(联网)。
解析:A(int& r): ref(r) {} 必须初始化列表。
排除法:引用天生必须初始化。
Vec operator+(const Vec& o) const 末尾 const 保证?
规则:末尾 const = 该 operator+ 不修改当前对象,符合 + 语义。
考点:重载 const。
解析:a+b 应产生新对象、不改 a/b;const 保证这点。
排除法:是「不修改自身」的承诺。
实现一个计数器类,最合理的封装是?
规则:数据私有 + 公有操作接口 = 封装。
考点:封装应用。
解析:private: int count; public: void add(){count++;} int get() const{return count;}。
排除法:公有数据破坏封装。
Date(int m) 构造中若 m 非法(如 13)应?
规则:构造函数适合做参数校验,保证对象创建后状态合法。
考点:构造校验。
解析:Date(int m): month(m){ if(m<1||m>12) month=1; }。
排除法:构造是初始化+校验的好位置。
小数据容器(如坐标 {x,y})只想存数据、无封装需求,用?
规则:纯数据容器用 struct(默认 public 少写);需要封装/不变量用 class。
考点:struct vs class 选型(联网)。
解析:struct Point{ int x,y; }; 简洁。
排除法:OOP 风格数据默认 public 用 struct。
已有 Rectangle(长宽、面积),要加 Square,最合理的是?
规则:Square 是 Rectangle 的特例 → 继承复用。
考点:继承应用。
解析:Square 继承 Rectangle 的成员与 area(),可约束长宽相等。
排除法:继承是复用首选。
多种图形(圆/矩形/三角)都要算面积,统一用基类接口调用,最佳做法?
规则:多态统一接口:基类虚函数 + 派生重写 + 基类指针调用。
考点:多态应用。
解析:vector<Shape*> shapes; for(auto s: shapes) s->area(); 各调各的。
排除法:switch 是过程式做法,扩展性差。
用类管理文件资源(构造打开、析构关闭),这叫什么?
规则:RAII = 资源在构造获取、析构释放,对象生命周期管理资源。
考点:RAII(联网)。
解析:class File{ FILE* f; public: File(n){f=fopen(n);} ~File(){fclose(f);} }; 用完自动关。
排除法:RAII 是 C++ 资源管理核心。
shared_ptr<A> p(new A); 与裸指针相比的好处是?
规则:shared_ptr 引用计数,最后一个释放时自动 delete,防泄漏/悬垂。
考点:智能指针(进阶)。
解析:多个 shared_ptr 共享对象,计数归零自动析构。
排除法:自动管理,无需手动 delete。
vector<A> v; v.push_back(a);(A 含指针成员、无深拷贝构造)可能?
规则:push_back 会拷贝对象;A 无深拷贝构造 → 浅拷贝 → 多元素共享指针。
考点:容器拷贝坑(联网)。
解析:vector 扩容/拷贝时逐成员复制,指针成员共享 → 析构双 delete。
排除法:这是常见真实 bug。
C++11 移动构造 A(A&& o) 与拷贝构造 A(const A& o) 的区别是?
规则:移动构造转移资源所有权(指针直接拿走),避免深拷贝开销。
考点:移动语义(联网)。
解析:A(A&& o): p(o.p) { o.p=nullptr; } 转移而非复制。
排除法:移动是优化,非复制。
STL 容器存自定义类对象(如 vector<Student>)要求类?
规则:STL 容器存对象要求可拷贝(拷贝构造/赋值可用)。
考点:类与 STL。
解析:push_back 拷贝入容器;类需可拷贝(默认即可,除非禁拷贝)。
排除法:可拷贝是基本要求。
class A { int x; char c; }; 对象大小 sizeof(A) 可能是?
规则:结构体对齐:int(4)+char(1)+padding(3)=8。
考点:对象内存对齐。
解析:成员按对齐规则排,char 后补 3 字节对齐到 4。
排除法:5 是没算对齐。
class A { virtual void f(); }; 的 sizeof(A) 通常?
规则:含虚函数 → 对象含 vptr(指向 vtable),大小 = 指针大小(64 位 8 字节)。
考点:vptr(联网)。
解析:空类 1 字节(占位),有虚函数加 vptr → 8 字节(64 位)。
排除法:vptr 是虚函数对象的隐藏成员。
class A { int x; }; 中 x 外部能访问吗?
规则:class 默认 private(struct 才默认 public)。
考点:默认访问易错。
解析:A a; a.x=5; 编译错误。
排除法:class 不是默认 public。
class A { public: A(int x){} }; A a; 会?
规则:定义了带参构造 → 无默认构造 → A a; 报错。
考点:默认构造消失易错。
解析:要支持 A a; 需手动加 A(){}。
排除法:这是最高频 C++ 坑。
类含 new 的指针成员但没写析构,对象销毁时?
规则:默认析构不释放堆内存 → 泄漏。
考点:析构与泄漏。
解析:~Arr() 没写 delete[],p 指向的内存永远不释放。
排除法:堆内存不会自动回收。
含指针成员、默认拷贝构造,Arr b=a; 后两个对象都析构,会?
规则:浅拷贝两对象同指针,各自析构 delete 同一块 → double free。
考点:浅拷贝双 delete。
解析:a.p==b.p,~Arr 两次 delete[] 同一地址 → 崩溃。
排除法:double free 是经典崩溃。
Student* p; 用 p.name 会?
规则:指针访问成员用 ->,p.name 语法错。
考点:访问符易错。
解析:p->name 等价 (*p).name。
排除法:指针必须 ->。
成员函数 void set(int x){ x = x; }(没写 this)结果是?
规则:x=x 是形参自赋值(同名遮蔽成员),成员未被修改。
考点:同名遮蔽。
解析:应写 this->x = x; 或改参数名。
排除法:裸 x 指最近的形参。
派生对象销毁时,析构顺序是?
规则:析构与构造相反:先 ~Derived 再 ~Base。
考点:析构顺序。
解析:Circle 销毁 → ~Circle(释放自己的)→ ~Shape。
排除法:与构造顺序相反。
const A a; a.set(1);(set 非 const)会?
规则:const 对象只能调 const 成员函数。
考点:const 对象限制。
解析:set 可能修改对象,const 对象禁止调。
排除法:编译期拦截。
A a1,a2; 两个对象访问 static 成员 count?
规则:static 成员所有对象共享一份。
考点:static 共享。
解析:a1.count++ 后 a2.count 也变。
排除法:static 是类级共享。
重载 operator+ 时返回类型应为?
规则:+ 应返回新对象(值或 const 值),不修改操作数。
考点:重载语义。
解析:a+b 产生新 Vec,不改 a/b;+= 才改自身返回引用。
排除法:+ 与 += 语义不同。
派生类能访问基类的?
规则:派生类可访问基类 public/protected,不可访问 private。
考点:继承访问(联网)。
解析:基类 private 只有基类自己能访问。
排除法:private 不出类。
struct A { private: int x; }; x 是?
规则:显式访问说明符覆盖默认;struct 默认 public 但写了 private 就私有。
考点:显式覆盖默认。
解析:struct 默认 public 是「没写时」;显式 private 生效。
排除法:显式声明优先。
explicit A(int) 后 A a(5) 和 A a = A(5) ?
规则:explicit 只阻止 A a = 5 隐式转换;显式构造都合法。
考点:explicit 范围。
解析:A(5) 显式调用合法;A a = 5 隐式被拦。
排除法:explicit 不管显式。
运行下面代码,输出是?
01class A { 02 int v; 03public: 04 A(int x): v(x) {} 05 A operator+(const A& o) const { return A(v + o.v); } 06 int get() const { return v; } 07}; 08int main(){ A a(2), b(3); A c = a + b + a; cout << c.get(); }
规则:operator+ 串联:a+b=(5),再+a=(7)。
考点:综合追踪。
解析:a+b → A(5);A(5)+a → A(5+2)=A(7)。
排除法:链式重载按顺序算。
下面代码输出几次「X」?(构造和析构各输出 X)
01class X { 02public: 03 X() { cout << "X"; } 04 X(const X&) { cout << "X"; } 05 ~X() { cout << "X"; } 06}; 07X f(X a) { return a; } 08int main(){ X x; f(x); }
规则:x 构造 1 次;f(x) 拷贝传参 1 次;返回可能拷贝;各临时析构。
考点:拷贝/析构次数(C++17 拷贝省略优化)。
解析:C++17 起返回值可能省略拷贝,最少 x 构造 + 传参拷贝 + 2~3 次析构 ≈ 3+ 次输出。
排除法:对象传值必涉及拷贝。
运行下面代码,输出?
01class Shape { public: virtual double area() const { return 0; } }; 02class Rect : public Shape { double w,h; public: Rect(double a,double b): w(a),h(b){} double area() const override { return w*h; } }; 03int main(){ Shape* s = new Rect(3,4); cout << s->area(); delete s; }
规则:虚函数 + 基类指针 → 调派生 Rect::area = 12。
考点:继承多态综合。
解析:3*4=12。
排除法:virtual 保证多态。
class A { public: A(int x){} }; A arr[3]; 会?
规则:对象数组要默认构造;类只有带参构造 → 报错。
考点:数组与默认构造。
解析:A arr[3] 无法逐个调带参构造 → 编译错误。
排除法:数组创建要求默认构造。
把构造函数设为 private,作用是?
规则:private 构造 → 外部不能创建对象,用于单例/工厂模式。
考点:private 构造(进阶)。
解析:class S { private: S(){} public: static S& get(){ static S s; return s; } };。
排除法:是设计模式技巧。
函数 void f(A a)(按值传对象)会?
规则:按值传对象 → 拷贝构造复制副本,函数内修改不影响原对象。
考点:按值传对象。
解析:要避免拷贝开销/要改原对象 → 传引用 void f(A& a)。
排除法:按值必拷贝。
A& f(A& a){ return a; } 返回引用,好处是?
规则:返回引用避免拷贝、可链式(如 operator<< 返回流引用)。
考点:返回引用。
解析:cout << a << b 靠 operator<< 返回 ostream&。
排除法:引用免拷贝。
C++ string 本质是?
规则:string 是封装动态字符数组的类,提供 size()/find()/+= 等成员。
考点:string 是类(KJ-20b 衔接)。
解析:s.size()、s1+s2 都是成员函数/运算符重载。
排除法:string 是类不是裸数组。
vector 相比裸数组的封装优势是?
规则:vector 是封装动态数组的类,管理 size/capacity 和扩容。
考点:容器封装。
解析:v.push_back(x) 自动处理扩容(倍增),使用者不用管内存。
排除法:封装带来便利,非速度。
「通过统一的接口调用不同实现」体现 OOP 的哪个特性?
规则:统一接口调不同实现 = 多态。
考点:特性识别(CSP-J 2022 考法)。
解析:Shape* s; s->area() 不同对象不同实现。
排除法:封装藏数据;继承复用;重载同名不同参。