• C++
  • C++中`freopen`函数的使用 接受一行数据但没给出个数”的情况

  • @ 2025-6-3 10:14:29

下面我将以小学生能理解的方式,详细讲解C++中freopen函数的使用,以及如何处理编程题中“接受一行数据但没给出个数”的情况。我们会用简单的例子和生动的比喻,让你轻松掌握这些知识!

一、什么是freopen?

想象你正在玩一个游戏,游戏里有一个“魔法门”。

  • 平时:你从键盘输入数字,程序把结果显示在屏幕上。
  • 用freopen后:你可以通过“魔法门”,让程序从文件读入数字,把结果写到另一个文件里,而不需要修改原来的代码!
#include <cstdio>   // 要使用freopen,必须包含这个“工具包”
#include <iostream> // 要使用cin/cout,也需要这个“工具包”
using namespace std;

int main() {
    // 打开“魔法门”,让程序从input.txt读数据
    freopen("input.txt", "r", stdin);  // stdin = 标准输入(原来默认是键盘)
    
    // 打开“魔法门”,让程序把结果写到output.txt
    freopen("output.txt", "w", stdout); // stdout = 标准输出(原来默认是屏幕)
    
    // 下面的代码和平时一样写!就像在和键盘、屏幕对话
    int a, b;
    cin >> a >> b;       // 从input.txt读入两个数
    cout << a + b << endl; // 把结果写到output.txt
    
    return 0;
}

二、为什么要用freopen?

比如你参加一个编程比赛,题目说:

输入:文件中第一行有两个整数a和b。
输出:输出到文件,a+b的结果。

如果你不用freopen

  • 每次测试都要手动输入数字,麻烦!
  • 比赛提交代码时,可能忘记删除调试用的cout,导致错误。

用freopen后

  • 本地测试时,直接从文件读数据,结果自动保存到文件,方便检查!
  • 比赛提交前,只要注释掉freopen那两行,代码就变回从键盘读、输出到屏幕,不会出错!

三、怎么处理“一行数据但没说有几个数”的情况?

问题描述

比如题目说:

输入:一行有若干个整数(个数不知道),用空格分开。
输出:这些数的和。

例子

  • 输入:3 1 5 2 → 输出:11
  • 输入:10 20 → 输出:30

关键思路

就像吃糖果一样

  • 只要“糖果盒”(输入流)里还有糖果(数字),就一直吃(读)!
  • 直到吃完所有糖果(遇到文件结尾)。

代码实现

#include <cstdio>
#include <iostream>
using namespace std;

int main() {
    // 考试时注释掉下面两行!平时调试时打开
    // freopen("input.txt", "r", stdin);
    // freopen("output.txt", "w", stdout);
    
    int sum = 0;  // 用来累加所有数的和
    int num;      // 临时存放每个读入的数
    
    // 重点!只要还能读到数,就一直循环
    while (cin >> num) {
        sum = sum + num;  // 把读到的数累加到sum里
    }
    
    cout << sum << endl;  // 输出总和
    return 0;
}

代码解释

  • while (cin >> num):就像问“还有数字吗?”,如果有就继续读。
  • sum = sum + num:每读到一个数,就加到总和里。
  • 当读到文件结尾(或键盘输入结束)时,循环自动停止。

四、本地测试时怎么准备文件?

  1. 创建input.txt
    用记事本写一行数字,比如:3 1 5 2,保存。

  2. 运行程序
    程序会自动读取input.txt,并把结果写入output.txt

  3. 检查output.txt
    打开output.txt,应该看到结果:11

五、比赛提交前要注意什么?

把这两行注释掉(或者用#ifdef条件编译):

// freopen("input.txt", "r", stdin);
// freopen("output.txt", "w", stdout);

这样提交的代码就会从键盘读入、输出到屏幕,符合比赛要求!

六、练习题目

题目1

输入一行若干个整数,输出其中的最大值。
输入:5 3 9 1 → 输出:9

题目2

输入一行若干个单词(用空格分开),输出单词的个数。
输入:hello world → 输出:2

提示:用string wordwhile (cin >> word)来读单词。

总结

  1. freopen的作用:通过“魔法门”让程序从文件读写,方便测试。
  2. 处理未知个数的输入:用while (cin >> x)一直读,直到读完所有数据。
  3. 比赛提交前:注释掉freopen语句,确保代码直接和键盘/屏幕交互。

如果有任何疑问,随时问我哦! 😊

1 条评论

  • @ 2025-6-3 10:18:13

    🧒 C++ freopen 教程(含编程题输入处理)


    🎯 一、什么是 freopen?为什么用它?

    想象一下:

    你平时写程序的时候,是自己在键盘上敲数据给电脑看。
    可是在做编程题的时候,比如 OJ(在线判题系统),你的程序要自动从一个文件里读数据,而不是等你手动输入。

    那怎么让程序自动读文件呢?这就用到了 freopen


    📌 freopen 是什么?

    • 它是一个函数,用来 重定向输入输出流
    • 简单来说:就是把本来应该从键盘输入的内容,改成从文件里读。
    • 把本来应该输出到屏幕的内容,改成输出到另一个文件。

    ✨ 基本语法(记住这三句):

    freopen("input.txt", "r", stdin);  // 把输入变成从 input.txt 文件读取
    freopen("output.txt", "w", stdout); // 把输出变成写入 output.txt 文件
    
    • "input.txt" 是你要读的输入文件。
    • "r" 表示 read(读)。
    • stdin 是标准输入(也就是键盘)。
    • 同理,"output.txt" 是输出文件,"w" 表示 write(写),stdout 是标准输出(屏幕)。

    🧸 示例:读取 input.txt 文件中的内容

    假设我们有一个 input.txt 文件,里面写着:

    Hello, world!
    

    我们可以这样读它:

    #include <cstdio>  // 因为要用 freopen 和 printf/scanf 等
    
    int main() {
        // 打开 input.txt 文件作为输入源
        freopen("input.txt", "r", stdin);
    
        char str[100];  // 准备一个容器装文字
        scanf("%s", str);  // 读取一个单词
        printf("读到的内容是:%s\n", str);  // 输出读到的内容
    
        return 0;
    }
    

    运行结果(假设 input.txt 内容是 Hello, world!):

    读到的内容是:Hello,
    

    注意:scanf("%s", ...) 只会读到空格前的部分。


    🎯 二、“输入一行数据但没告诉个数”是什么意思?

    有时候题目会说:

    输入一行整数,以空格分隔,请输出它们的总和。

    比如输入可能是这样的:

    3 5 7 2 9
    

    或者更长一点:

    1 2 3 4 5 6 7 8 9 10
    

    但我们不知道有多少个数字,怎么办?


    💡 思路:

    我们可以用一个循环,每次读一个数,直到这一行结束为止。

    在 C++ 中可以用 while (scanf("%d", &x) != EOF) 或者配合 cin 来处理。


    🧸 小学生版解释:

    就像你吃糖豆子一样:

    豆子放在碗里,你一个一个地吃,吃到碗空了就停下。

    我们也可以一个一个地读数字,直到这一行读完为止。


    ✅ 示例代码:读取一行未知数量的整数,并求和

    #include <cstdio>
    
    int main() {
        // 如果你在本地测试,想从文件读数据,可以加上:
        // freopen("input.txt", "r", stdin);
    
        int x;
        int sum = 0;
    
        // 每次尝试读一个整数,如果读不到就停下来
        while (scanf("%d", &x) != EOF) {
            sum += x;  // 把这个数加进总和
        }
    
        printf("这些数的总和是:%d\n", sum);
        return 0;
    }
    

    📌 举个例子:

    如果你输入的是:

    3 5 7 2 9
    

    程序就会计算:

    3 + 5 + 7 + 2 + 9 = 26
    

    🚨 特别注意:

    • scanf("%d", &x) 返回值不是 EOF(End Of File)表示还有数据可读。
    • 当你从控制台输入时,按下 Ctrl+Z(Windows)或 Ctrl+D(Linux/macOS)表示输入结束。

    🧩 三、综合实战:从文件读一行数字并求和

    我们做一个完整的例子:

    📁 input.txt 文件内容:

    10 20 30 40 50
    

    ✅ C++ 程序如下:

    #include <cstdio>
    
    int main() {
        // 从 input.txt 读取输入
        freopen("input.txt", "r", stdin);
    
        int x;
        int sum = 0;
    
        // 一直读数字,直到文件结尾
        while (scanf("%d", &x) != EOF) {
            sum += x;
        }
    
        printf("所有数字的总和是:%d\n", sum);
        return 0;
    }
    

    🔍 输出结果:

    所有数字的总和是:150
    

    🧠 总结一下知识点(小学生口诀版)

    项目 内容
    freopen 是啥? 把键盘换成文件读写
    freopen("in.txt", "r", stdin) 输入来自 in.txt 文件
    scanf("%d", &x) 读一个整数
    while(scanf(...) != EOF) 一直读,直到文件结束
    题目没说多少个数怎么办? 一个一个读,读完为止

    📚 作业时间(动手练练)

    你可以试着完成以下任务:

    1. 编写程序,读取一行整数,输出最大值。
    2. 编写程序,读取一行整数,统计个数。
    3. 编写程序,读取两行整数,分别求和并比较哪一行大。

    如果你完成了这些任务,恭喜你已经掌握了一项非常实用的编程技巧啦!


    需要我帮你检查代码或者出题练习吗?随时告诉我 😄

    • 1