文件顺序读取--函数解析

fgetc和fputc 函数

fgetcfputc是C语言中用于文件操作的函数,分别用于从文件中读取字符和向文件中写入字符。以下是这两个函数的详细原型和说明:

fgetc函数原型

int fgetc(FILE *stream);

参数说明

  • FILE *stream:一个指向FILE对象的指针,该对象指定了一个文件流。这个流应该是已经打开的,以便进行读取。

返回值

  • 如果读取成功,返回读取的字符(以unsigned char强制转换为int的形式)。
  • 如果到达文件末尾或发生错误,返回EOF(通常定义为-1)。

fputc函数原型

int fputc(int character, FILE *stream);

参数说明

  • int character:需要写入的字符。虽然传入参数定义为int类型,实际上它只会使用该int参数的低8位,将其当作无符号字符来处理。
  • FILE *stream:要写入字符的文件流。可以是用标准库函数fopen打开的文件,也可以是类似stdinstdoutstderr之类的预定义文件流。

返回值

  • 如果写入成功,返回写入的字符(作为unsigned char类型转换为int类型)。
  • 如果写入失败,返回EOF(通常定义为-1)。

总结

  • fgetc函数用于从指定的文件流中读取下一个字符。
  • fputc函数用于将指定的字符写入到指定的文件流中。

这两个函数在处理文件时非常有用,可以单独使用或结合其他文件操作函数一起使用。它们通常用于处理二进制文件和文本文件。

简单应用

**题目:**打开一个名为"a.txt"的源文件以读取数据,然后打开(或创建)一个名为"b.txt"的目标文件以写入数据。

题目解析:

  1. 使用一个while循环,在循环中,使用fgetc函数从源文件中读取一个字符,并检查是否读取到了文件结束符(EOF)。如果没有读取到EOF,我们就使用fputc函数将该字符写入到目标文件中。
  2. 最后,我们关闭两个文件,并输出一条消息表示文件复制完成。

代码实现:

#include <stdio.h>  
#include <stdlib.h>  
int main() {  
    FILE *sourceFile, *targetFile;  
    char ch;  
  
    // 打开源文件  
    sourceFile = fopen("a.txt", "r");  
    if (sourceFile == NULL) {  
        perror("Error opening source file");  
        return EXIT_FAILURE;  
    }  
  
    // 打开目标文件(如果文件不存在,将创建它)  
    targetFile = fopen("b.txt", "w");  
    if (targetFile == NULL) {  
        perror("Error opening target file");  
        fclose(sourceFile); // 关闭已打开的源文件  
        return EXIT_FAILURE;  
    }  
  
    // 使用fgetc从源文件中读取字符,并使用fputc写入到目标文件中  
    while ((ch = fgetc(sourceFile)) != EOF) {  
        fputc(ch, targetFile);  
    }  
  
    // 关闭文件  
    fclose(sourceFile);  
    fclose(targetFile);  
  
    printf("File copy complete!\n");  
  
    return 0;  
}
a文件内容复制后b文件内容
在这里插入图片描述在这里插入图片描述

fgets和fputs函数

fgetsfputs是C语言中用于文件操作的函数,分别用于从文件中读取一行字符串和向文件中写入一个字符串。以下是这两个函数的详细原型和说明:

fgets函数原型

char *fgets(char *str, int n, FILE *stream);

参数说明

  1. char *str:指向一个字符数组的指针,用于存储从文件读取的字符串。
  2. int n:要读取的最大字符数(包括最后的空字符\0)。
  3. FILE *stream:指向FILE对象的指针,标识了要从中读取字符的文件流。

返回值

  • 如果成功,返回指向读取的字符串的指针(即str参数的值)。
  • 如果到达文件末尾或发生错误,返回NULL

fputs函数原型

int fputs(const char *s, FILE *stream);

参数说明

  1. const char *s:指向要写入的字符串的指针。
  2. FILE *stream:指向FILE对象的指针,指定了要将字符串写入的文件流。

返回值

  • 如果成功,返回非负整数。
  • 如果发生错误,返回EOF(一个定义在stdio.h中的特殊值,通常为-1)。

总结

  • fgets函数用于从指定的文件流中读取一行字符串,直到遇到换行符、文件结束或读取了n-1个字符。
  • fputs函数用于将一个字符串写入到指定的文件流中,不包括字符串的终止空字符\0

这两个函数在处理文本文件时特别有用,fgets常用于按行读取文本内容,而fputs则用于将字符串写入文件。注意,使用这两个函数时应确保文件流已正确打开,且在使用完毕后应关闭文件流以避免资源泄漏。

简单应用

题目:使用fgets函数从文件aa.txt中读取内容,并使用fputs函数将内容写入另一个文件bb.txt中。

题目解析:

  1. 首先定义了源文件和目标文件的文件名(这里分别为"aa.txt"和"bb.txt"),然后定义了一个用于暂存读取内容的字符数组buffer,并指定了其大小为1024字节。
  2. 接着,我们使用fopen函数以只读模式(“r”)打开源文件,并以写入模式(“w”)打开目标文件。如果文件打开失败,程序将输出错误消息并退出。
  3. 然后,我们使用fgets函数从源文件中读取内容到buffer中,并使用fputs函数将内容写入到目标文件中。这个操作在一个循环中进行,直到源文件的所有内容都被读取并写入到目标文件中。
  4. 最后,我们使用fclose函数关闭源文件和目标文件,并输出一条消息表示文件复制完成。
#include <stdio.h>  
#include <stdlib.h>  
#include <string.h>  
  
#define BUFFER_SIZE 1024 // 缓冲区大小  
  
int main() {  
    FILE *sourceFile, *targetFile;  
    char buffer[BUFFER_SIZE];   
  
    // 打开源文件  
    sourceFile = fopen("aa.txt", "r");  
    if (sourceFile == NULL) {  //打开失败判断
        perror("Error opening source file");  
        return EXIT_FAILURE;  
    }  
  
    // 打开目标文件(如果文件不存在,将创建它)  
    targetFile = fopen("bb.txt", "w");  
    if (targetFile == NULL) {  
        perror("Error opening target file");  
        fclose(sourceFile); // 关闭已打开的源文件  
        return EXIT_FAILURE;  
    }  
  
    // 使用fgets循环读取源文件内容存放在buffer数组中  
    while ((fgets(buffer, BUFFER_SIZE, sourceFile)) != NULL) {  
        // 使用fputs将读取的内容(即buffer的内容)写入目标文件  
        fputs(buffer, targetFile);  
    }  
  
    // 关闭文件  
    fclose(sourceFile);  
    fclose(targetFile);  
  
    printf("File copy complete!\n");  
  
    return 0;  
}

运行结果:

aa.txt原来的内容复制后bb.txt的内容
在这里插入图片描述在这里插入图片描述

fread 和fwrite 函数

freadfwrite是C语言中用于文件操作的重要函数,它们分别用于从文件中读取数据块和向文件中写入数据块。以下是这两个函数的详细原型和说明:

fread 函数原型

size_t fread(void *ptr, size_t size, size_t count, FILE *stream);

参数说明

  1. void *ptr:这是一个指向内存空间的指针,该内存空间用于储存从文件中读取的数据块。由于ptrvoid *类型,它可以指向任何数据类型。
  2. size_t size:这指定了每个从文件读取的数据项的字节大小。size_t是一个无符号整数类型,通常用于表示对象的大小。
  3. size_t count:这指定了从文件读取的数据项的个数。
  4. FILE *stream:这是一个指向FILE类型结构的指针,它指定了fread函数要读取的文件流,该值通常是fopen函数的返回值。

返回值

  • 如果成功,fread函数返回实际读取的数据项个数(以size_t类型返回)。
  • 如果读取到文件末尾或发生错误,返回值可能小于count

fwrite 函数原型

size_t fwrite(const void *ptr, size_t size, size_t count, FILE *stream);

参数说明

  1. const void *ptr:这是一个指向内存空间的指针,该内存空间中储存有待写入文件的数据块。由于ptrconst void *类型,它可以指向任何数据类型的常量。
  2. size_t size:这指定了每个待写入文件的数据项的字节大小。
  3. size_t count:这指定了待写入文件的数据项的个数。
  4. FILE *stream:这是一个指向FILE类型结构的指针,它指定了fwrite函数要写入的文件流。

返回值

  • 如果成功,fwrite函数返回实际写入的数据项个数(以size_t类型返回)。
  • 如果写入过程中发生错误,返回值可能小于count

总结

  • freadfwrite函数都用于处理二进制文件,可以读写任意类型的数据。
  • 这两个函数都使用size_t类型来表示数据项的大小和数量,确保可以处理大文件。
  • 在使用这两个函数时,需要注意文件指针stream必须已经被正确打开,并且具有适当的读写权限。
  • 这两个函数都是块操作,比逐个字符操作的fgetcfputc函数在处理大文件时更加高效。

函数应用

若使用同样的案例,那么只要修改代码为

#include <stdio.h>  
#include <stdlib.h>  
  
#define BUFFER_SIZE 1024 // 缓冲区大小  
  
int main() {  
    FILE *sourceFile, *targetFile;  
    char buffer[BUFFER_SIZE];  
    size_t bytesRead;  
  
    // 打开源文件  
    sourceFile = fopen("aa.txt", "rb"); // 使用二进制模式读取  
    if (sourceFile == NULL) {  
        perror("Error opening source file");  
        return EXIT_FAILURE;  
    }  
  
    // 打开目标文件(如果文件不存在,将创建它)  
    targetFile = fopen("bb.txt", "wb"); // 使用二进制模式写入  
    if (targetFile == NULL) {  
        perror("Error opening target file");  
        fclose(sourceFile); // 关闭已打开的源文件  
        return EXIT_FAILURE;  
    }  
  
    // 使用fread从源文件中读取数据块,并使用fwrite写入到目标文件中  
    while ((bytesRead = fread(buffer, sizeof(char), BUFFER_SIZE, sourceFile)) > 0) {  
        fwrite(buffer, sizeof(char), bytesRead, targetFile);  
    }  
  
    // 关闭文件  
    fclose(sourceFile);  
    fclose(targetFile);  
  
    printf("File copy complete!\n");  
  
    return EXIT_SUCCESS;  
}

注意,这里我们使用了二进制模式(“rb"和"wb”)来打开文件,这允许我们处理任何类型的数据,包括文本和二进制数据。

fscanf和fprintf函数

fscanffprintf是C语言中用于文件操作的重要函数,分别用于从文件中读取格式化的输入和向文件中写入格式化的输出。以下是这两个函数的详细原型和说明:

fscanf 函数原型

int fscanf(FILE *stream, const char *format, ...);

参数说明

  1. FILE *stream:这是一个指向FILE对象的指针,该对象标识了要从中读取数据的文件流。
  2. const char *format:这是一个C字符串,包含了要被读取的数据的格式。这个字符串可以包含普通字符(这些字符会被简单地复制到输出流中)和格式控制符(这些字符指定了如何从输入流中读取和解释数据)。
  3. ...:这是一个可变参数列表,包含了指向要存储读取数据的变量的指针。这些变量的类型和数量由format字符串中的格式控制符决定。

返回值

  • 如果成功,fscanf函数返回成功读取并赋值的参数数量
  • 如果在读取过程中遇到文件结束或发生错误,则返回EOF(通常定义为-1)。

fprintf 函数原型

int fprintf(FILE *stream, const char *format, ...);

参数说明

  1. FILE *stream:这是一个指向FILE对象的指针,该对象标识了要将数据写入其中的文件流。
  2. const char *format:这是一个C字符串,包含了要被写入到流stream中的文本。它可以包含嵌入的格式标签,这些标签会被随后的附加参数中指定的值替换,并按需进行格式化。
  3. ...:这是一个可变参数列表,包含了要写入文件的数据。这些数据的类型和数量由format字符串中的格式控制符决定。

返回值

  • 如果成功,fprintf函数返回写入的字符数(不包括字符串结束符\0)。
  • 如果发生错误,返回一个负值。

总结

  • fscanffprintf函数都使用FILE指针来指定操作的文件流。
  • 这两个函数都接受一个格式字符串,该字符串定义了如何读取或写入数据。
  • 这两个函数都接受可变数量的参数,这些参数的类型和数量由格式字符串中的格式控制符决定。
  • fscanf用于从文件中读取格式化的数据,而fprintf用于向文件中写入格式化的数据。

注意:这两个函数在处理文件时都依赖于文件的当前位置。如果你需要从文件的特定位置开始读取或写入,你需要使用fseek函数来设置文件的位置指针。

应用示例

学生成绩管理系统

项目描述:

这个简单的项目将模拟一个学生成绩管理系统的部分功能。它从一个名为input.txt的文本文件中读取学生的姓名和成绩,然后输出每个学生的姓名和成绩到控制台。之后,它将这些信息写入到另一个名为output.txt的文本文件中。

文本文件(input.txt)格式:

张三 90  
李四 85  
王五 92  
赵六 78

每行包含学生的姓名和成绩,用空格分隔。

在这里插入图片描述

代码实现:

#include <stdio.h>  
#include <stdlib.h>  
  
#define MAX_LINE_LENGTH 100  
  
int main() {  
    FILE *inputFile, *outputFile;  
    char line[MAX_LINE_LENGTH];  
    char name[50];  
    int score;  
  
    // 打开输入文件  
    inputFile = fopen("input.txt", "r");  
    if (inputFile == NULL) {  
        printf("Error opening input file");  //或者perror
        return 1;  
    }  
  
    // 打开输出文件  
    outputFile = fopen("output.txt", "w");  
    if (outputFile == NULL) {  
        printf("Error opening output file");  
        fclose(inputFile); // 不要忘记关闭已打开的文件  
        return 1;  
    }  
  
    // 读取并处理文件内容  
    while (fscanf(inputFile, "%49s %d", name, &score) == 2) {  
        // 在控制台输出学生姓名和成绩  
        printf("Name: %s, Score: %d\n", name, score);  
  
        // 将学生姓名和成绩写入到输出文件  
        fprintf(outputFile, "Name: %s, Score: %d\n", name, score);  
    }  
  
    // 关闭文件  
    fclose(inputFile);  
    fclose(outputFile);  
  
    printf("Data processing completed successfully.\n");  
  
    return 0;  
}

运行后:output.txt中的文本内容

在这里插入图片描述

注意事项:

  1. 在使用fscanf时,我们指定了%49s来读取学生的姓名,这是为了防止输入过长导致缓冲区溢出。49是因为我们为name数组预留了一个位置给字符串结束符\0

  2. 我们检查fscanf的返回值是否为2,以确保我们成功读取了一个姓名和一个成绩。

  3. 使用printf(或perror)函数来输出打开文件时发生的错误。

  4. 始终在不再需要文件时关闭它,以避免资源泄露。
    fclose(inputFile);
    fclose(outputFile);

  5. 考虑到错误处理,如果无法打开文件,则程序会输出一个错误消息并返回非零值。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

小邹子

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值