C++ 基本的输入输出
C++ 基本的输入输出
C++ 的 I/O 发生在流中,流是字节序列。如果字节流是从设备(如键盘、磁盘驱动器、网络连接等)流向内存,这叫做输入操作。如果字节流是从内存流向设备(如显示屏、打印机、磁盘驱动器、网络连接等),这叫做输出操作。
C++ 编译器根据要输出变量的数据类型,选择合适的流插入运算符来显示值。<<
运算符被重载来输出内置类型(整型、浮点型、double 型、字符串和指针)的数据项。
流插入运算符 <<
在一个语句中可以多次使用,如上面实例中所示,endl
用于在行末添加一个换行符。
I/O 库头文件
头文件 | 函数和描述 |
---|---|
<iostream> |
该文件定义了 cin 、cout 、cerr 和 clog 对象,分别对应于标准输入流、标准输出流、非缓冲标准错误流和缓冲标准错误流。 |
<iomanip> |
该文件通过所谓的参数化的流操纵器(比如 setw 和 setprecision ),来声明对执行标准化 I/O 有用的服务。 |
<fstream> |
该文件为用户控制的文件处理声明服务。我们将在文件和流的相关章节讨论它的细节。 |
标准输入输出
流 | 描述 |
---|---|
cin | 标准输入流 |
cout | 标准输出流 |
cerr | 标准错误(输出)流 |
clog | 标准日志记录(输出)流 |
我们将详细只看到cout
和cin
(标准输出和输入流); cerr
并且clog
也是输出流,因此它们基本上是一样的cout
,唯一的区别是它们为特定目的识别流:错误消息和记录; 在许多情况下,在大多数环境设置中,它们实际上完全相同:它们在屏幕上打印,尽管它们也可以单独重定向
cout
在大多数程序环境中,默认情况下标准输出是屏幕,并且定义为访问它的C++
流对象是cout
对于格式化输出操作,cout
与插入操作符一起使用,写入为<<
(即两个“小于”符号)。
cout << "Output sentence"; // prints Output sentence on screen
cout << 120; // prints number 120 on screen
cout << x; // prints the value of x on screen
多个插入操作符<<
可以链接在一个语句中:
cout << "This " << " is a " << "single C++ statement";
链接插入对于在单个语句中混合文字和变量特别有用:
int age = 24;
string zipcode = "90064";
cout << "I am " << age << " years old and my zipcode is " << zipcode;
//I am 24 years old and my zipcode is 90064
cout不会自动执行的操作是在末尾添加换行符,除非指示这样做。
换行
要插入换行符,应在行应断开的确切位置插入换行符。在C++中,可以将换行符指定为\n
。
cout << "First sentence.\n";
cout << "Second sentence.\nThird sentence.";
或者使用endl
操作符
cout << "First sentence." << endl;
cout << "Second sentence." << endl;
该操纵器产生一个新行字符,完全一样的插入确实; 但它还有一个额外的行为:流的缓冲区(如果有的话)被刷新(flushed),这意味着输出请求被写入设备,如果它还没有。这主要影响完全缓冲的流,并且(通常)不是完全缓冲的流。尽管如此,不管刷新流是不是一个特征,使用它通常都是一个不错的选择。请记住,冲洗(flush)操作会产生一定的开销,并且在某些设备上可能会产生延迟。
标准输入cin
预定义的对象 cin
是 iostream 类的一个实例。cin
对象附属到标准输入设备,通常是键盘。cin
是与流提取运算符 >>
结合使用的,
// i/o example
#include <iostream>
using namespace std;
int main ()
{
int i;
cout << "Please enter an integer value: ";
cin >> i;
cout << "The value you entered is " << i;
cout << " and its double is " << i*2 << ".\n";
return 0;
}
正如您所看到的,从中提取cin似乎使得从标准输入获取输入的任务变得非常简单和直接。但这种方法也有很大的缺点。如果用户输入了无法解释为整数的其他内容,上面的示例会发生什么?那么,在这种情况下,提取操作失败。默认情况下,这使程序继续运行而不设置变量i值,如果i稍后使用该值,则会产生未确定的结果。所以好的程序是需要对用户的输入进行处理的。
cin >> name >> age;
这相当于下面两个语句:
cin >> name;
cin >> age;
cin和字符串
string mystring;
cin >> mystring;
但是,cin
提取始终将空格(空格,制表符,换行符...)视为终止要提取的值,因此提取字符串意味着始终提取单个单词,而不是短语或整个句子。
整行字符串输入
为了获得整行cin,存在一个函数,称为getline,将stream(cin)作为第一个参数,将字符串变量作为第二个参数。
// cin with strings
#include <iostream>
#include <string>
using namespace std;
int main ()
{
string mystr;
cout << "What's your name? ";
getline (cin, mystr);
cout << "Hello " << mystr << ".\n";
cout << "What is your favorite team? ";
getline (cin, mystr);
cout << "I like " << mystr << " too!\n";
return 0;
}
请注意,在两次调用中getline
,我们使用相同的字符串标识符mystr
。程序在第二次调用中所做的只是将之前的内容替换为引入的新内容。
字符串流
标准头<sstream>
定义了一种类型,称为stringstream
允许将字符串视为流,从而允许从/向字符串提取或插入,其操作方式与执行cin
和执行cout
相同。此功能对于将字符串转换为数字值非常有用,反之亦然。例如,为了从字符串中提取整数,我们可以写:
// stringstreams
#include <iostream>
#include <string>
#include <sstream>
using namespace std;
int main ()
{
string mystr;
float price=0;
int quantity=0;
cout << "Enter price: ";
getline (cin,mystr);
stringstream(mystr) >> price;
cout << "Enter quantity: ";
getline (cin,mystr);
stringstream(mystr) >> quantity;
cout << "Total price: " << price*quantity << endl;
return 0;
}
标准错误流(cerr)
预定义的对象 cerr
是 iostream 类的一个实例。cerr
对象附属到标准错误设备,通常也是显示屏,但是 cerr
对象是非缓冲的,且每个流插入到 cerr
都会立即输出。
cerr
也是与流插入运算符 <<
结合使用的。
#include <iostream>
using namespace std;
int main( )
{
char str[] = "Unable to read....";
cerr << "Error message : " << str << endl;
}
标准日志流(clog)
预定义的对象 clog 是 iostream 类的一个实例。clog 对象附属到标准错误设备,通常也是显示屏,但是 clog 对象是缓冲的。这意味着每个流插入到 clog 都会先存储在缓冲在,直到缓冲填满或者缓冲区刷新时才会输出。
clog 也是与流插入运算符 << 结合使用的,如下所示:
实例
#include <iostream>
using namespace std;
int main( )
{
char str[] = "Unable to read....";
clog << "Error message : " << str << endl;
}
当上面的代码被编译和执行时,它会产生下列结果:
Error message : Unable to read....
通过这些小实例,我们无法区分
cout
、cerr
和clog
的差异,但在编写和执行大型程序时,它们之间的差异就变得非常明显。所以良好的编程实践告诉我们,使用 cerr 流来显示错误消息,而其他的日志消息则使用 clog 流来输出。