- 新增现代 C++ 教程的 Preface 章节,包括英文和中文版本 - 添加 C++ Primer 练习代码 - 新增 Learn C++ 教程的 C++ 开发简介章节 - 添加头文件解析文档 - 更新 mkdocs.yml,包含新教程的目录结构 - 修改项目设置,使用 Python 3.10环境
477 lines
10 KiB
Markdown
477 lines
10 KiB
Markdown
---
|
||
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 << "Hello,World" << 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加到100,sum的终值是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
|
||
编译并运行本节的程序,给它输入全都相等的值。再次运行程序,输入没有重复的值。
|
||
|
||
解:
|
||

|
||
|
||
|
||

|
||
|
||
## 练习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`头文件,编译并运行本节给出的书店程序。
|