C++中的cin和cout:常见用法与进阶技巧
cin
和cout
作为最简单的两类语句,不过是输入一个变量,进行运算。但是当输入变得复杂时,我们如何存储和处理这些变量呢?本文将结合网易某真题带你学习cin和cout的进阶处理。参考博文:每日一题:魔法王国游历问题
在C++编程中,cin
和cout
是最常用的输入输出工具。它们分别用于从标准输入读取数据和向标准输出写入数据。本文将结合一个具体的问题,介绍cin
和cout
的常见用法,并深入探讨一些进阶技巧。同时,我们还会讨论如何初始化数组,包括固定数值、可变数组以及bool
类型的初始化。
1. cin和cout的常见用法
1.1 基本输入输出
cin
和cout
是C++标准库中的输入输出流对象,分别定义在<iostream>
头文件中。cin
用于从标准输入(通常是键盘)读取数据,而cout
用于向标准输出(通常是屏幕)写入数据。
#include <iostream>
using namespace std;
int main() {
int n;
cout << "请输入一个整数: ";
cin >> n;
cout << "你输入的整数是: " << n << endl;
return 0;
}
在这个例子中,cin >> n
从标准输入读取一个整数并存储在变量n
中,cout << "你输入的整数是: " << n << endl;
则输出这个整数。
1.2 多变量输入
cin
可以连续读取多个变量,只需使用>>
操作符分隔即可。
int a, b;
cin >> a >> b;
这段代码会依次读取两个整数并分别存储在a
和b
中。
1.3 结合问题的输入
题目描述
魔法王国有 n
个城市,编号为 0
到 n-1
,城市之间的道路连接构成一棵树。小易从 0
号城市出发,最多可以行动 L
次,每次行动可以走到一个相邻的城市。目标是计算小易最多能游历多少个城市(每个城市只计算一次)。参考博文:每日一题:魔法王国游历问题
输入说明
- 第一行输入两个整数
n
和L
:n
表示城市数量(2 ≤ n ≤ 50
)。L
表示小易最多可以行动的次数(1 ≤ L ≤ 100
)。
- 第二行输入
n-1
个整数parent[i]
:parent[i]
表示(i+1)
号城市的父节点是parent[i]
,即(i+1)
号城市与parent[i]
号城市之间有一条边。- 输入示例:45 73
0 0 0 1 0 0 3 5 6 8 7 9 1 10 1 2 15 6 8 11 14 17 8 14 3 21 23 3 21 15 12 5 21 31 11 13 7 17 20 26 28 16 36 26
对于动不动几十上百个输入而言,我们该如何接收和存储这些数据呢?我们可以直接用一个数组进行存储,之后再进行处理。
for(int i=0; i<n; i++)
{
cin << parent[i];
}
也可以直接按照题目要去对于数据进行处理。
int n, L;
cin >> n >> L;
bool* adj = new bool[n * n];
for (int i = 1; i < n; ++i)
{
int parent;
cin >> parent;
adj[parent * n + i] = true;
}
在给定的代码片段中,cin
用于读取两个整数n
和L
,然后读取n-1
个整数来构建邻接矩阵。
这里,cin >> parent
读取每个父节点的索引,并将其用于构建邻接矩阵。
2. cin和cout的进阶用法
2.1 格式化输出
cout
支持多种格式化输出方式,例如设置宽度、精度、填充字符等。
cout << setw(10) << setfill('*') << 123 << endl;
这段代码会输出*******123
,其中setw(10)
设置输出宽度为10,setfill('*')
设置填充字符为*
。
2.2 输入流的错误处理
cin
在读取数据时可能会遇到错误,例如输入类型不匹配。我们可以使用cin.fail()
来检查输入是否失败,并使用cin.clear()
和cin.ignore()
来清除错误状态和忽略无效输入。
int num;
while (true) {
cout << "请输入一个整数: ";
cin >> num;
if (cin.fail()) {
cin.clear(); // 清除错误状态
cin.ignore(numeric_limits<streamsize>::max(), '\n'); // 忽略无效输入
cout << "输入无效,请重新输入。" << endl;
} else {
break;
}
}
2.3 输入输出重定向
cin
和cout
可以重定向到文件或其他流。例如,将输入从文件读取,输出写入文件。
freopen("input.txt", "r", stdin);
freopen("output.txt", "w", stdout);
int n;
cin >> n;
cout << "读取的整数是: " << n << endl;
3. 数组的初始化
3.1 固定数值初始化
在C++中,输入输出的时候,无法避免要对于数组等容器进行初始化。对于普通数组而言,可以使用花括号{}
来初始化数组。
int arr[5] = {1, 2, 3, 4, 5};
3.2 可变数组初始化
对于动态分配的数组,可以使用new
关键字来分配内存,并使用循环或memset
进行初始化。
int* arr = new int[n];
for (int i = 0; i < n; ++i) {
arr[i] = 0; // 初始化为0
}
3.3 初始化bool数组
bool
数组的初始化可以使用memset
函数,将数组的所有元素设置为false
。
bool* adj = new bool[n * n];
memset(adj, false, sizeof(bool) * n * n);
3.4 memset和sizeof(bool)
memset
函数用于将内存块的每个字节设置为指定的值。sizeof(bool)
返回bool
类型的大小(通常为1字节)。因此,memset(adj, false, sizeof(bool) * n * n)
将adj
数组的所有元素设置为false
。
memset(adj, false, sizeof(bool) * n * n);
这段代码的作用是将adj
数组的所有元素初始化为false
。sizeof(bool) * n * n
计算了数组的总字节数,确保memset
正确地覆盖整个数组。
3.3 初始化vector数组
对于动态数组而言,初始化方法较多,以下简要介绍两种最常见的方式。对于更详细的介绍,可以查看此博文:C++动态数组初始化:std::vector一维与二维的操作指南
3.3.1 指定大小初始化
可以指定 std::vector
的大小,所有元素会被默认初始化为 0(对于基本类型)。
vector<int> vec(10); // 初始化大小为 10,所有元素为 0
3.3.2 指定大小和初始值
可以在初始化时指定大小和初始值。
vector<int> vec(10, 5); // 初始化大小为 10,所有元素为 5
4. 总结
cin
和cout
是C++中最基本的输入输出工具,掌握它们的常见用法和进阶技巧对于编写高效的C++程序至关重要。此外,数组的初始化也是编程中的常见操作,理解如何正确初始化数组(尤其是bool
数组)可以帮助我们避免许多潜在的错误。
希望本文对你理解cin
和cout
的用法以及数组的初始化有所帮助。如果你有任何问题或建议,欢迎在评论区留言讨论!点个赞吧
