火龙信奥
  • 分享
  • 课程
  • 题库
  • 打卡
    • 代码对战
    • 快速对战
  • 题单
  • 团队
  • 荣誉墙
  • 商城
  • 登录 / 注册

第五章 C++ 输入与输出

作者: 作者的头像   huolong , 时间:2026-08-20 18:04:46 , 所有人可见, 阅读  54

第五章 C++ 输入与输出

在 C++ 中,数据的输入与输出是程序与外界交互的唯一桥梁。C++ 同时继承了 C 语言的高效输入输出库 <cstdio>,并提供了面向对象的流输入输出库 <iostream>。本章将详细讲解这两套输入输出系统的使用方法、格式化排版技术以及竞赛中至关重要的效率优化技巧。


5.1 使用标准输入/输出(C 风格)

标准输入输出使用 C 语言传统的高效库。 * 头文件:<cstdio> * 变量约定: * 可以使用文件指针 FILE *fin, *fout; 分别代表输入文件和输出文件。 * 在标准的控制台读写中,将它们替换为 stdin 和 stdout,即代表从键盘输入以及输出到屏幕。

1. 格式化输出:printf / fprintf

输出字符串或变量的值可以使用:

printf("格式字符串", 变量1, 变量2, ...);
// 或者输出到指定文件指针 fout 中
fprintf(fout, "格式字符串", 变量1, 变量2, ...);
常用格式占位符:
格式字符 含义 格式字符 含义
%d 有符号十进制整数 %e / %E 用科学记数法表示的浮点数(小写/大写)
%u 无符号十进制整数 %f 浮点数(float 或 double)
%o 八进制无符号整数 %c 单个字符
%x / %X 十六进制无符号整数(小写/大写) %s 字符串(字符数组)
常用格式修饰符:
  • %5d:右对齐输出至少占用 5 位宽度的整数。若实际位数不足 5 位,左侧用空格补齐;若实际位数超过 5 位,则按实际位数完整输出。
  • %-5d:左对齐输出至少占用 5 位宽度的整数。若实际位数不足 5 位,右侧用空格补齐;若实际位数超过 5 位,则按实际位数完整输出。
  • %05d:右对齐输出至少占用 5 位宽度的整数。若实际位数不足 5 位,左侧用字符 '0' 补齐;若实际位数超过 5 位,则按实际位数完整输出。
  • %+d:输出整数时,无论正数还是负数,都显式输出其正负号。
  • %.2f:保留 2 位小数输出浮点数。若小数部分超过 2 位则四舍五入;若不足 2 位则在末尾用 0 补全。

2. 格式化输入:scanf / fscanf

用于从标准输入或文件中读取变量值。

scanf("格式字符串", &变量1, &变量2, ...);
// 或者从指定文件指针 fin 中读取
fscanf(fin, "格式字符串", &变量1, &变量2, ...);
  • 地址符 & 警告:在使用 scanf 或 fscanf 读入基本类型变量(如 int, double, char 等)时,千万不要漏掉取地址运算符 &。因为 printf 传递的是变量的值,而 scanf 必须接收变量的内存地址才能将读入的值写入。
  • 返回值说明:scanf 和 fscanf 的返回值是成功输入并赋值的变量个数。若读取到文件末尾无数据可读时,fscanf 会返回常量值 EOF(通常定义为 -1)。
  • 分界符特征:scanf 和 fscanf 会自动忽略前导的制表符(TAB)、空格和回车。在读取数据时,一旦遇到这些空白字符,就会停止当前变量的读取。

3. 读取单个字符:fgetc

  • 使用 fgetc(fin) 可以从输入流中读取下一个字符。
  • 正确流程:在读取时,应该先将返回值存入 int 类型的变量中,并首先判断该返回值是否等于 EOF。在确认不是 EOF 后,再通过强制类型转换将其转换为 char 类型使用。
  • 跨平台换行符差异: 不同操作系统在文本文件中的行末换行符标准并不统一,处理单字符读入时需特别注意:
    • Linux 系统:换行符为 \n(ASCII 10)。
    • macOS 系统:换行符为 \r(ASCII 13)。
    • Windows 系统:换行符由连续的两个字符组成,依次为 \r 和 \n。

5.2 使用流输入/输出(C++ 风格)

C++ 提供了更加类型安全、书写简便的输入输出流。 * 头文件:<iostream>

1. 基础读写操作

  • 输入到变量:cin >> n;
  • 输出到屏幕:cout << a;
  • 连续链式读写: cpp cin >> n >> m; cout << a << ',' << b << "\n";
  • 关于换行:在输出换行时,建议直接输出字符串 "\n"。由于 std::endl 在换行的同时会强行刷新输出缓冲区(flush),在大量输出时会导致效率显著降低。

2. 格式化输出控制

  • 头文件:<iomanip>
长度与对齐控制:

若要实现右对齐、占用 $n$ 位长度、不足部分用特定字符补齐,可以按如下方式调用:

cout.width(n);
cout.fill(' '); // 如果想用 "0" 补齐,可以将空格换成 '0'
cout << a;

注意:cout.width(n) 仅对紧随其后的那一次输出生效,每次输出前都需要重新调用。

输出多进制数:

C++ 允许通过流操纵算子直接改变整数的输出进制: * 八进制输出:cout << oct << a; * 十六进制输出:cout << hex << a; * 其余进制(如二进制、三进制等)需要手动编写转换算法实现。

3. 性能优化提示

在数据规模非常大(例如读入或输出量达到 $10^5$ 级别以上)时,C++ 默认的输入输出流由于需要与 C 的标准输入输出保持同步,速度会变得非常慢,极易导致程序运行超时(TLE)。

在 main 函数的开头加上以下语句,可以取消同步并解除 cin 与 cout 的绑定,使流读写速度达到与 scanf 和 printf 相当的水平:

ios::sync_with_stdio(false);
cin.tie(nullptr);

安全警告:调用 ios::sync_with_stdio(false) 之后,禁止在同一个程序中混合使用 C 风格的输入输出(如 scanf / printf)和 C++ 风格的输入输出(如 cin / cout),否则会导致输出顺序错乱。


5.3 课后推荐练习题

通过以下题目,可以练习各种输入输出格式(如保留小数、指定格式对齐、应对大输入量时的效率优化等):

  • 题目编号:1 —— A+B Problem
    • 考点:最基础的输入与输出。可以使用 scanf / printf 或 cin / cout 来完成两数读入和求和输出。
  • 题目编号:3 —— 读入一个浮点数,保留 2 位小数
    • 考点:练习控制浮点数输出精度。使用 C 风格的 %.2f 或 C++ 风格的 fixed 与 setprecision(2) 进行格式化输出。
  • 题目编号:7 —— 计算圆的面积
    • 考点:需要根据输入的半径计算面积并精确保留四位小数,适合练习精度控制修饰符。
  • 题目编号:12 —— 钞票分解
    • 考点:题目对输出格式有严格要求,需要输出固定的拼写与空格,非常适合练习整除、求模以及 printf 格式化字符串的精确排版。
  • 题目编号:166 —— 区间和询问
    • 考点:本题的数据规模较大($N, M \le 100,000$)。如果不进行输入输出优化,使用未经加速的 cin 和 cout 极易超时。适合练习 scanf/printf 或流加速语句。
  • 题目编号:228 —— 数字金字塔
    • 考点:需要按照金字塔的形状进行对齐输出,每一行前的空格数和数字间的空格有着严格的排版规律,是练习输出宽度控制的优秀题目。

—— 本文来自火龙信奥(义乌睿码科技):义乌青少年信息学奥赛与编程教育平台,专注 CSP-J/S、NOIP、GESP 竞赛培训,线上线下融合教学,助力编程升学。网址:hlcoding.com

关于火龙

  • 关于我们
  • 学员获奖
  • 预约试听
  • ACM课程
  • CSP课程
  • 学习指南

帮助中心

  • 用户协议
  • 打字练习
  • 在线画图
  • DevC++下载
  • CSP报名
  • GESP官网

推荐课程

  • C++零基础入门(可试看)
  • C++进阶提升
  • GESP考级辅导
  • GESP打卡
  • CSP-J/S打卡

公众号

火龙信奥公众号二维码

地址:义乌市北门街188号新天地商厦二楼2F 邮箱:wdlok305@126.com

© 2017-2026 义乌市睿码科技有限公司版权所有 浙ICP备2021013995号

火龙信奥
请输入登录信息


请完成安全验证
验证码底图 滑块
向右拖动滑块完成验证
请输入用户名 / 绑定的手机号码



请输入注册信息(手机号验证码注册)





验证码5分钟有效,60秒内不可重复获取,每日最多3次

微信登录

微信登录二维码

正在生成二维码...

账号已过期,请续期。
去续期

绑定手机号

📱

为了更好地保护您的账号安全,享受完整的平台服务

请您尽快绑定手机号码