sairate 4108f6c42d docs(book): 添加现代 C++教程及相关代码
- 新增现代 C++ 教程的 Preface 章节,包括英文和中文版本
- 添加 C++ Primer 练习代码
- 新增 Learn C++ 教程的 C++ 开发简介章节
- 添加头文件解析文档
- 更新 mkdocs.yml,包含新教程的目录结构
- 修改项目设置,使用 Python 3.10环境
2025-07-06 16:14:43 +08:00

477 lines
10 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

---
sort: 1
---
# 开始
## 练习1.1
查阅你使用的编译器的文档确定它所使用的文件名约定。编译并运行第2页的main程序。
解:
- ``g++ 1.1.cpp -o main``
- ``./main``
## 练习1.2
改写程序,让它返回-1。返回值-1通常被当做程序错误的标识。重新编译并运行你的程序观察你的系统如何处理main返回的错误标识。
解:
- 在ubuntu下使用g++,返回-1``./main``没有发现任何异常。
- ``echo $?``返回255。
## 练习1.3
编写程序在标准输出上打印Hello, World。
解:
```cpp
#include <iostream>
int main()
{
std::cout << "HelloWorld" << std::endl;
return 0;
}
```
## 练习1.4
我们的程序使用加法运算符`+`来将两个数相加。编写程序使用乘法运算符`*`,来打印两个数的积。
解:
```cpp
#include <iostream>
int main() {
std::cout << "Enter two numbers" << std::endl;
int v1 = 0, v2 = 0;
std::cin>> v1 >> v2;
std::cout << "The product of " << v1 << " and " << v2 << " is "<< v1 * v2 << std::endl;
}
```
## 练习1.5
我们将所有的输出操作放在一条很长的语句中,重写程序,将每个运算对象的打印操作放在一条独立的语句中。
解:
```cpp
#include <iostream>
int main()
{
std::cout << "Enter two numbers" << std::endl;
int v1 = 0, v2 = 0;
std::cin >> v1 >> v2;
std::cout << "The product of ";
std::cout << v1;
std::cout << " and ";
std::cout << v2;
std::cout << " is ";
std::cout << v1 * v2;
std::cout << std::endl;
}
```
## 练习1.6
解释下面程序片段是否合法。
```cpp
std::cout << "The sum of " << v1;
<< " and " << v2;
<< " is " << v1 + v2 << std::endl;
```
如果程序是合法的,它的输出是什么?如果程序不合法,原因何在?应该如何修正?
解:
程序不合法,有多余的分号,修改如下:
```cpp
std::cout << "The sum of " << v1
<< " and " << v2
<< " is " << v1 + v2 << std::endl;
```
## 练习1.7
编译一个包含不正确的嵌套注释的程序,观察编译器返回的错误信息。
解:
```cpp
/* 正常注释 /* 嵌套注释 */ 正常注释*/
```
错误信息:
```
/* 正常注释 /* 嵌套注释 */ 正常注释*/
^
ch1.cpp:97:37: error: stray \255 in program
ch1.cpp:97:37: error: stray \243 in program
ch1.cpp:97:37: error: stray \345 in program
ch1.cpp:97:37: error: stray \270 in program
ch1.cpp:97:37: error: stray \270 in program
ch1.cpp:97:37: error: stray \346 in program
ch1.cpp:97:37: error: stray \263 in program
ch1.cpp:97:37: error: stray \250 in program
ch1.cpp:97:37: error: stray \351 in program
ch1.cpp:97:37: error: stray \207 in program
ch1.cpp:97:37: error: stray \212 in program
ch1.cpp: In function int main():
ch1.cpp:97:50: error: expected primary-expression before / token
/* 正常注释 /* 嵌套注释 */ 正常注释*/
^
ch1.cpp:98:5: error: expected primary-expression before return
return 0;
^
```
## 练习1.8
指出下列哪些输出语句是合法的(如果有的话):
```cpp
std::cout << "/*";
std::cout << "*/";
std::cout << /* "*/" */;
std::cout << /* "*/" /* "/*" */;
```
预测编译这些语句会产生什么样的结果,实际编译这些语句来验证你的答案(编写一个小程序,每次将上述一条语句作为其主体),改正每个编译错误。
解:
只有第三句编译出错,改成如下即可:
```cpp
std::cout << /* "*/" */";
```
第四句等价于输出 `" /* "`
## 练习1.9
编写程序,使用`while`循环将50到100整数相加。
解:
```cpp
#include <iostream>
int main() {
int i = 50, sum = 0;
while (i <= 100) {
sum += i;
i += 1;
}
std::cout << "sum is " << sum << std::endl;
}
```
## 练习1.10
除了`++`运算符将运算对象的值增加1之外还有一个递减运算符`--`实现将值减少1.编写程序与使用递减运算符在循环中按递减顺序打印出10到0之间的整数。
解:
```cpp
#include <iostream>
int main() {
int i = 10;
while (i >= 0) {
std::cout << i << std::endl;
i--;
}
}
```
## 练习1.11
编写程序,提示用户输入两个整数,打印出这两个整数所指定的范围内的所有整数。
解:
```cpp
#include <iostream>
int main() {
int temp = 0;
std::cout << "Please enter two numbers"<< std::endl;
int v1 = 0, v2 = 0;
std::cin >> v1 >> v2;
// 若v1 > v2,则调换顺序
if (v1 > v2) {
temp = v2;
v2 = v1;
v1 = temp;
}
while (v1 <= v2){
std::cout << v1 << std::endl;
v1 += 1;
}
}
```
## 练习1.12
下面的for循环完成了什么功能sum的终值是多少
```cpp
int sum = 0;
for (int i = -100; i <= 100; ++i)
sum += i;
```
解:
从-100加到100sum的终值是0。
## 练习1.13
使用for循环重做1.4.1节中的所有练习练习1.9到1.11)。
解:
### 练习1.9
```cpp
#include <iostream>
// 修改1.9
int main() {
int sum = 0;
for (int i = 50; i <= 100; i++) {
sum += i;
}
std::cout << "sum is " << sum << std::endl;
}
```
### 练习1.10
```cpp
#include <iostream>
int main() {
for (int i = 10; i >= 0; i--) {
std::cout << i << std::endl;
}
}
```
### 练习1.11
```cpp
#include <iostream>
int main() {
int temp = 0;
std::cout << "Please enter two numbers"<< std::endl;
int v1 = 0, v2 = 0;
std::cin >> v1 >> v2;
// 若v1 > v2,则调换顺序
if (v1 > v2) {
temp = v2;
v2 = v1;
v1 = temp;
}
for (;v1 <= v2;v1++){
std::cout << v1 << std::endl;
}
}
```
## 练习1.14
对比for循环和while循环两种形式的优缺点各是什么
解:
- <https://stackoverflow.com/questions/2950931/for-vs-while-in-c-programming>
-
```
The main difference between the `for`'s and the `while`'s is a matter of pragmatics:
we usually use `for` when there is a known number of iterations,
and use `while` constructs when the number of iterations in not known in advance.
The `while` vs `do ... while` issue is also of pragmatics,
the second executes the instructions once at start,
and afterwards it behaves just like the simple `while`.
```
## 练习1.15
编写程序包含第14页“再探编译”中讨论的常见错误。熟悉编译器生成的错误信息。
解:
编译器可以检查出的错误有:
- 语法错误
- 类型错误
- 声明错误
## 练习1.16
编写程序从cin读取一组数输出其和。
解:
```cpp
#include <iostream>
int main() {
int sum = 0, value = 0;
while(std::cin >> value) {
sum += value;
}
std::cout << "sum is " << sum << std::endl;
return 0;
}
```
## 练习1.17
如果输入的所有值都是相等的,本节的程序会输出什么?如果没有重复值,输出又会是怎样的?
## 练习1.18
编译并运行本节的程序,给它输入全都相等的值。再次运行程序,输入没有重复的值。
解:
![20220512125903-2022-05-12-12-59-04](https://cdn.jsdelivr.net/gh/ironartisan/picRepo/20220512125903-2022-05-12-12-59-04.png)
![20220512130841-2022-05-12-13-08-42](https://cdn.jsdelivr.net/gh/ironartisan/picRepo/20220512130841-2022-05-12-13-08-42.png)
## 练习1.19
修改你为1.4.1节练习1.11第11页所编写的程序打印一个范围内的数使其能处理用户输入的第一个数比第二个数小的情况。
解:
```cpp
#include <iostream>
int main()
{
int start = 0, end = 0;
std::cout << "Please input two num: ";
std::cin >> start >> end;
if (start <= end) {
while (start <= end){
std::cout << start << " ";
++start;
}
std::cout << std::endl;
}
else{
std::cout << "start should be smaller than end !!!";
}
}
```
## 练习1.20
在网站http://www.informit.com/title/032174113 上第1章的代码目录包含了头文件 Sales_item.h。将它拷贝到你自己的工作目录中。用它编写一个程序读取一组书籍销售记录将每条记录打印到标准输出上。
解:
```cpp
#include <iostream>
#include "Sales_item.h"
int main()
{
for (Sales_item item; std::cin >> item; std::cout << item << std::endl);
return 0;
}
```
命令:
```
./main < data/add_item
```
输出:
```
0-201-78345-X 3 60 20
0-201-78345-X 2 50 25
```
## 练习1.21
编写程序,读取两个 ISBN 相同的 Sales_item 对象,输出他们的和。
解:
```cpp
#include <iostream>
#include "Sales_item.h"
int main()
{
Sales_item item_1;
Sales_item item_2;
std::cin >> item_1;
std::cout << item_1 << std::endl;
std::cin >> item_2;
std::cout << item_2 << std::endl;
std::cout << "sum of sale items: " << item_1 + item_2 << std::endl;
return 0;
}
```
命令:
```
./main < data/add_item
```
输出:
```
0-201-78345-X 3 60 20
0-201-78345-X 2 50 25
sum of sale items: 0-201-78345-X 5 110 22
```
## 练习1.22
编写程序,读取多个具有相同 ISBN 的销售记录,输出所有记录的和。
解:
```cpp
#include <iostream>
#include "Sales_item.h"
int main() {
Sales_item sum_item;
for (Sales_item item; std::cin >> item; std::cout << item << std::endl) {
sum_item += item;
}
std::cout << "sum is " << sum_item << std::endl;
return 0;
}
```
## 练习1.23
编写程序,读取多条销售记录,并统计每个 ISBN每本书有几条销售记录。
## 练习1.24
输入表示多个 ISBN 的多条销售记录来测试上一个程序,每个 ISBN 的记录应该聚在一起。
解:
```cpp
#include <iostream>
#include "Sales_item.h"
int main()
{
Sales_item total;
if (std::cin >> total){
Sales_item trans;
while (std::cin >> trans){
if (total.isbn() == trans.isbn()) {
total += trans;
}
else {
std::cout << total << std::endl;
total = trans;
}
}
std::cout << total << std::endl;
}
else {
std::cerr << "No data?!" << std::endl;
return -1;
}
return 0;
}
```
```
## 练习1.25
借助网站上的`Sales_item.h`头文件,编译并运行本节给出的书店程序。