C++基础知识总结(超详细整理)
1. C++语言核心特性
| 特性 | 描述 | 示例场景 |
|---|---|---|
| 面向对象(OOP) | 支持类、继承、多态、封装,通过class关键字定义对象类型。 |
设计一个Car类,封装品牌、速度、加速方法 |
| 泛型编程(模板) | 使用template可实现类型无关、可重用的算法和容器。 |
template<typename T> T max(T a, T b) |
| 性能可控 | 支持手动内存管理和低级操作,可精细控制性能开销。 | 使用new/delete或RAII实现资源管理 |
| 兼容C语言 | 与C语言高度兼容,可调用C库函数,平滑迁移遗留C代码。 | 在C++中#include <stdio.h>并使用printf |
| 标准库(STL) | 提供容器、算法、迭代器等丰富组件,简化常见数据结构与算法实现。 | 使用std::vector<int>存储动态数组 |
| RAII | 通过对象构造/析构管理资源,避免泄漏。 | std::lock_guard<std::mutex>管理互斥锁 |
| 多范式支持 | 支持过程式、面向对象、泛型、函数式编程风格。 | 使用std::function和lambda表达式 |
| 编译期检查与优化 | 模板和内联函数在编译期实例化和展开,可实现零开销抽象;编译器提供多种优化选项。 | inline函数在调用处展开,消除函数调用开销 |
2. C++基本语法
2.1 标识符与关键字
- 标识符:字母、数字、下划线组合,且不能以数字开头;区分大小写;与关键字不冲突。
- 常用关键字示例:
int,char,class,public,private,template,virtual,if,for,while,return。
2.2 注释
cpp
// 单行注释
/* 多行注释
可跨多行 */
2.3 基本数据类型
| 类型 | 大小(典型) | 取值范围 |
|---|---|---|
char |
1 byte | -128 ~ 127 或 0 ~ 255 |
int |
4 bytes | -2^31 ~ 2^31-1 |
short |
2 bytes | -2^15 ~ 2^15-1 |
long |
8 bytes | -2^63 ~ 2^63-1 |
float |
4 bytes | 单精度浮点 |
double |
8 bytes | 双精度浮点 |
bool |
1 byte | true/false |
2.4 变量与常量
cpp
int x = 10; // 变量初始化
const double PI = 3.14159; // 常量声明
2.5 运算符
- 算术:
+,-,*,/,% - 关系:
==,!=,<,>,<=,>= - 逻辑:
&&,||,! - 位运算:
&,|,^,~,<<,>> - 赋值:
=,+=,-=,*=,/=,%= - 其他:
?:(三元)、sizeof、typeid
2.6 控制流
cpp
if (a > b) {
// ...
} else if (a == b) {
// ...
} else {
// ...
}
switch (c) {
case 0: doA(); break;
case 1: doB(); break;
default: doDefault();
}
for (int i = 0; i < n; ++i) {
// ...
}
while (cond) {
// ...
}
do {
// ...
} while (cond);
3. 指针与引用
3.1 指针
cpp
int a = 5;
int* p = &a; // p指向a
*p = 10; // 通过指针修改a的值
nullptr表示空指针- 指针算术:
p + 1指向下一个同类型元素
3.2 引用
cpp
int b = 20;
int& r = b; // r是b的引用
r = 30; // b变为30
- 引用必须初始化且不能重新绑定
4. 函数与重载
cpp
int add(int a, int b) {
return a + b;
}
// 函数重载
double add(double a, double b) {
return a + b;
}
- 默认参数:
void f(int x = 0) - 内联函数:
inline int f() { return 0; } - 递归函数:支持函数自己调用自身
5. 类与对象
5.1 类定义
cpp
class Person {
public:
Person(const std::string& name, int age)
: name(name), age(age) {}
void introduce() const {
std::cout << "Name: " << name << ", Age: " << age << std::endl;
}
private:
std::string name;
int age;
};
5.2 继承与多态
cpp
class Student : public Person {
public:
Student(const std::string& n, int a, const std::string& sid)
: Person(n, a), studentId(sid) {}
void introduce() const override {
Person::introduce();
std::cout << "ID: " << studentId << std::endl;
}
private:
std::string studentId;
};
- 虚函数:
virtual void func(); - 纯虚函数:
virtual void func() = 0; - 抽象类:包含至少一个纯虚函数
6. 模板与STL
6.1 函数模板
cpp
template<typename T>
T Max(T a, T b) {
return a > b ? a : b;
}
6.2 类模板
cpp
template<typename T>
class Stack {
public:
void push(const T& x) { data.push_back(x); }
void pop() { data.pop_back(); }
private:
std::vector<T> data;
};
6.3 常用STL容器
std::vector,std::list,std::dequestd::map,std::unordered_map,std::set- 算法:
std::sort,std::find,std::for_each
7. 内存管理与RAII
new/delete,new[]/delete[]- 智能指针:
std::unique_ptr,std::shared_ptr,std::weak_ptr - RAII:资源获取即初始化,依赖析构自动释放
8. 异常处理
cpp
try {
mayThrow();
} catch (const std::exception& e) {
std::cerr << e.what() << std::endl;
} catch (...) {
std::cerr << "Unknown error" << std::endl;
}
9. 输入输出
cpp
#include <iostream>
std::cout << "Hello" << std::endl;
std::cin >> x;
#include <fstream>
std::ifstream in("input.txt");
std::ofstream out("output.txt");
10. 编译与调试
- 常用命令:
g++ -std=c++17 main.cpp -o app - 调试:
gdb,valgrind检测内存问题
C++基础知识练习(共30题)
包含选择题、判断题、填空题、简答题、编程题,并附参考答案与简要解析。
一、选择题(每题2分,共10分)
-
下列关于引用的说法正确的是:
A. 引用可以重新绑定到其他对象
B. 引用必须在定义时初始化
C. 引用可以为null
D. 引用大小不定
答案:B
解析:引用必须初始化且不可更改绑定对象。 -
下列哪个不是有效的C++标准类型?
A.
long longB.
char16_tC.
byteD.
wchar_t答案:C
解析 :byte为C++17新增枚举类std::byte,但不是关键字类型。 -
表达式
sizeof(int*)的结果通常是:A. 4
B. 8
C. 1
D. 与平台相关
答案:D
解析:指针大小与平台和编译器有关。 -
下列容器中,不保证元素连续存储的是:
A.
std::vectorB.
std::dequeC.
std::stringD.
std::array答案:B
解析 :deque底层分块存储,不连续。 -
下列代码输出是什么?
cpp
int x = 1;
std::cout << ++x << x++;
A. 12
B. 22
C. 未定义行为
D. 11
答案:C
解析:同一表达式中多次修改并读取无序,导致未定义行为。
二、判断题(每题1分,共5分)
| 序号 | 题目 | 正误 |
|---|---|---|
| 1 | C++中,virtual关键字用于声明虚函数和实现多态。 |
✔ |
| 2 | 在栈上分配的对象需要手动调用delete释放。 |
✘ |
| 3 | std::unique_ptr可被复制赋值。 |
✘ |
| 4 | 函数模板可以重载普通函数。 | ✔ |
| 5 | auto关键字可用于变量类型推断。 |
✔ |
解析:
- 正确;
- 栈上对象自动析构;
unique_ptr不可拷贝;- 模板与函数重载可共存;
auto启用编译器类型推断。
三、填空题(每题2分,共10分)
-
C++11新增的范围for循环语法为
______。答案 :
for (auto& x : container) -
std::vector扩容时,通常是原容量的______倍。答案:2
-
使用
new[]分配的动态数组应使用______释放。答案 :
delete[] -
在类中,声明纯虚函数使用语法
______。答案 :
virtual void func() = 0; -
std::map底层实现通常是红黑树,插入和查找平均时间复杂度为______。答案:O(log n)
四、简答题(每题4分,共20分)
-
解释RAII的概念及其优点。
-
简述C++的三向绞接(Rule of Three/Five/Zero)。
-
比较
std::vector与std::list的使用场景和性能特点。 -
描述虚函数表(vtable)如何支持运行时多态。
-
简述C++对象的内存布局(对象头、成员变量、对齐)。
五、编程题(每题5分,共25分)
- 实现函数
countChars(const std::string& s),统计字符串中各字符出现次数,返回std::unordered_map<char, int>。
cpp
std::unordered_map<char,int> countChars(const std::string& s) {
std::unordered_map<char,int> freq;
for (char c : s) freq[c]++;
return freq;
}
- 编写线程安全单例类
Singleton,采用双重检查锁定。
cpp
class Singleton {
public:
static Singleton& getInstance() {
static std::mutex mtx;
if (!instance) {
std::lock_guard<std::mutex> lock(mtx);
if (!instance) instance = new Singleton();
}
return *instance;
}
private:
Singleton() {}
static Singleton* instance;
};
Singleton* Singleton::instance = nullptr;
- 写一个模板函数
swapElements,交换任意容器中两元素。
cpp
template<typename C>
void swapElements(C& container, size_t i, size_t j) {
std::swap(container[i], container[j]);
}
- 实现一个简单的智能指针类
UniquePtr<T>,支持析构时释放资源。
cpp
template<typename T>
class UniquePtr {
public:
explicit UniquePtr(T* ptr = nullptr) : ptr(ptr) {}
~UniquePtr() { delete ptr; }
T& operator*() const { return *ptr; }
T* operator->() const { return ptr; }
// 禁止拷贝
UniquePtr(const UniquePtr&) = delete;
UniquePtr& operator=(const UniquePtr&) = delete;
private:
T* ptr;
};
- 实现函数
isPrime(int n),判断素数,返回bool。
cpp
bool isPrime(int n) {
if (n < 2) return false;
for (int i = 2; i*i <= n; ++i) {
if (n % i == 0) return false;
}
return true;
}