当前位置: 首页 > news >正文

应用——文件I/O操作代码

文件I/O操作代码分析

一、基础文件操作

1. 打开文件 -01open.c

#include <fcntl.h> #include <stdio.h> int main(int argc, char **argv) { int fd = open("1.txt", O_WRONLY | O_CREAT | O_TRUNC, 0666); if (-1 == fd) { fprintf(stderr, "open error\n"); return 1; } return 0; }

知识点

  • open():系统调用打开文件

  • flags参数

    • O_WRONLY:只写模式

    • O_CREAT:文件不存在时创建

    • O_TRUNC:清空文件内容

  • mode参数0666表示文件权限(用户、组、其他都可读写)

  • 文件描述符:成功返回非负整数,失败返回-1

2. 写入文件 -04write.c

#include <fcntl.h> #include <stdio.h> int main(int argc, char **argv) { int fd = open("1.txt", O_WRONLY | O_CREAT | O_TRUNC, 0666); char str[100] = "hello"; ssize_t ret = write(fd, str, strlen(str)); printf("写入了%ld字节到文件", ret); close(fd); return 0; }

知识点

  • write(fd, buf, count):写入数据

  • strlen(str)vssizeof(str)

    • strlen(str):实际字符串长度(不包括'\0')

    • sizeof(str):数组总大小(100字节)

  • ssize_t:有符号整数类型,表示实际写入字节数

  • 必须调用close(fd)释放资源

3. 读取文件 -05read.c

#include <fcntl.h> #include <stdio.h> int main(int argc, char **argv) { int fd = open("/etc/passwd", O_RDONLY); char buf[50] = {0}; while (1) { bzero(buf, sizeof(buf)); // 清空缓冲区 int ret = read(fd, buf, sizeof(buf)-1); // 留一个位置给'\0' if (ret <= 0) break; printf("[%d]:{%s}", ret, buf); } close(fd); return 0; }

知识点

  • read(fd, buf, count):读取数据

  • 缓冲区清空

    • bzero(buf, sizeof(buf)):将内存清零

    • memset(buf, 0, sizeof(buf)):功能相同

  • 读取策略sizeof(buf)-1保留一个字节给字符串结束符

  • 返回值

    • >0:实际读取字节数

    • =0:文件结束

    • <0:错误

4. 文件复制 -06read_cp.c

#include <fcntl.h> #include <stdio.h> int main(int argc, char **argv) { if (argc < 3) { printf("usage: ./a.out srcfile dstfile\n"); } int fd_src = open(argv[1], O_RDONLY); int fd_dst = open(argv[2], O_WRONLY | O_CREAT | O_TRUNC, 0666); while (1) { char buffer[1024] = {0}; int ret = read(fd_src, buffer, sizeof(buffer)); if (ret <= 0) break; write(fd_dst, buffer, ret); } close(fd_dst); close(fd_src); return 0; }

知识点

  • 命令行参数argv[1]源文件,argv[2]目标文件

  • 分块读取:循环读取直到文件结束

  • 精确写入write(fd_dst, buffer, ret)只写入实际读取的字节

  • 资源管理:最后关闭两个文件描述符

二、高级文件操作

1. 文件插入 -02insert_file.c

#include <fcntl.h> #include <stdio.h> int main(int argc, char **argv) { FILE* fp = fopen("1.txt", "r+"); // 获取文件大小 fseek(fp, 0, SEEK_END); long size = ftell(fp); int pos = 15; char insert_str[100] = "hello"; // 保存后半部分内容 fseek(fp, pos, SEEK_SET); char *data = (char*)malloc(size); fread(data, size-pos, 1, fp); // 插入内容 fseek(fp, pos, SEEK_SET); fwrite(insert_str, strlen(insert_str), 1, fp); fwrite(data, size-pos, 1, fp); fclose(fp); free(data); return 0; }

知识点

  • 标准I/O:使用fopen()fread()fwrite()

  • 文件定位

    • fseek(fp, 0, SEEK_END):移动到文件末尾

    • ftell(fp):获取当前位置(即文件大小)

  • 插入策略

    1. 读取插入点之后的内容到内存

    2. 在插入点写入新内容

    3. 追加原来的后半部分内容

  • 内存管理:使用malloc()动态分配,最后free()

2. 文件定位 -08lseek.c

#include <fcntl.h> #include <stdio.h> int main(int argc, char **argv) { int fd = open("1.txt", O_RDWR); // 获取文件大小 long size = lseek(fd, 0, SEEK_END); printf("size %ld\n", size); // 移动到指定位置并写入 lseek(fd, 1024*1024, SEEK_SET); char str[] = "老孙到此一游"; write(fd, str, strlen(str)); close(fd); return 0; }

知识点

  • lseek(fd, offset, whence):移动文件指针

    • SEEK_SET:从文件开头

    • SEEK_CUR:从当前位置

    • SEEK_END:从文件末尾

  • 空洞文件:跳过大量字节后写入,中间部分会被填'\0'

  • 文件大小:使用lseek(fd, 0, SEEK_END)获取文件大小

三、标准输入输出

07stdin.c

#include <fcntl.h> #include <stdio.h> int main(int argc, char **argv) { char buf[10] = {0}; printf("pls input num:"); fflush(stdout); // 强制刷新缓冲区 read(0, buf, sizeof(buf)); // 从标准输入读取 int num = atoi(buf); write(2, &num, 4); // 写入标准错误 return 0; }

知识点

  • 标准文件描述符

    • 0:标准输入(stdin)

    • 1:标准输出(stdout)

    • 2:标准错误(stderr)

  • 缓冲机制

    • printf()输出到缓冲区,需要刷新才能显示

    • fflush(stdout)强制刷新输出缓冲区

  • 字符串转换atoi()将字符串转换为整数

  • 系统调用读写read()/write()也可以操作标准输入输出

四、应用实例

字典程序 -03dict.c

#include <stdio.h> #include <stdlib.h> #include <string.h> #include "list.h" typedef struct { char word[50]; char mean[512]; struct list_head node; } DATATYPE; int main(int argc, char** argv) { // 1. 打开字典文件 FILE* fp = fopen("/home/linux/dict.txt", "r"); // 2. 初始化链表 struct list_head dict_head; INIT_LIST_HEAD(&dict_head); // 3. 读取并存储字典数据 while (1) { char str[1024] = {0}; if (NULL == fgets(str, sizeof(str), fp)) break; char* word = strtok(str, " "); char* mean = strtok(NULL, "\r"); add_word(&dict_head, word, mean); } // 4. 用户查询交互 while (1) { char want_word[50] = {0}; printf("pls input want_word:"); fgets(want_word, sizeof(want_word), stdin); want_word[strlen(want_word) - 1] = '\0'; // 去掉换行符 if (0 == strcmp(want_word, "#quit")) break; DATATYPE* tmp = find_word(&dict_head, want_word); if (NULL == tmp) { printf("cant find word:%s\n", want_word); } else { printf("word:%s mean:%s\n", tmp->word, tmp->mean); } } return 0; }

核心知识点

  1. 文件读取

    • fgets(str, sizeof(str), fp):安全读取一行

    • 检查NULL判断文件结束// 原始格式:单词 解释\r\n

  2. char* word = strtok(str, " "); // 第一个空格前是单词 char* mean = strtok(NULL, "\r"); // 到\r前是解释 fgets(want_word, sizeof(want_word), stdin);
  3. want_word[strlen(want_word) - 1] = '\0'; // 去掉末尾的换行符
  4. 链表操作

    • list_add(&p->node, head):添加到链表

    • list_for_each_entry_safe():安全遍历链表

五、重要总结

1. 系统调用 vs 标准I/O

操作系统调用标准I/O
打开open()fopen()
读取read()fread()
写入write()fwrite()
关闭close()fclose()
定位lseek()fseek()

2. 常用文件打开模式

模式说明
O_RDONLY只读
O_WRONLY只写
O_RDWR读写
O_CREAT不存在时创建
O_TRUNC清空文件
O_APPEND追加模式

3. 错误处理模式

int fd = open("file.txt", O_RDONLY); if (-1 == fd) { perror("open failed"); // 自动添加错误信息 // 或 fprintf(stderr, "open error: %s\n", strerror(errno)); return 1; }

4. 内存与文件操作注意事项

  1. 缓冲区管理:读取前清空,写入时注意长度

  2. 资源释放:打开后必须关闭,分配后必须释放

  3. 错误检查:每个系统调用都可能失败

  4. 边界检查:防止缓冲区溢出

  5. 文件权限:创建文件时指定合适的权限

http://www.cnnetsun.cn/news/2508.html

相关文章:

  • SpringBoot3+Vue3新闻动态网站
  • 销售年终汇报再也不难写:AI自动把你的业绩转成完整PPT
  • 高性能ESAM芯片LKT4305GM
  • 销售年终总结PPT这样做最快:AI一键生成,从业绩到亮点全自动呈现
  • 销售工作太杂做不出PPT?AI自动帮你生成逻辑清晰的年终总结
  • 指针,不多的记录
  • Pandas库和画图
  • 第三方库Numpy
  • 中年危局:当职场抛弃你,比你想象的更早——一场静悄悄的社会性“死亡“
  • 项目解决方案:某湖泊AI微光增强水域监控解决方案
  • 协作传感加密密钥更新最佳实践(20年安全专家亲授)
  • 资源利用率提升80%?:深度解析量子-经典混合分配新范式
  • 量子编程调试技术深度解析(90%开发者忽略的关键细节)
  • 从下单到签收缩短40%时间:揭秘头部企业物流网络调度模型
  • 2030年网络安全倒计时:边缘量子密钥存储部署为何必须现在启动?
  • 为什么90%的量子编程课程失败?:教育设计中的4大盲区必须避开
  • 结构电池性能预测误差深度解析(误差来源全曝光)
  • 为什么你的AI服务在云端总崩溃?揭开故障转移配置的3个致命盲区
  • 【金融交易量子加速的安全验证】:揭秘量子计算时代下金融系统安全的十大挑战与应对策略
  • 【智慧城市安全防线】:如何在3步内实现RBAC与ABAC融合管控
  • 错过等于落后十年:量子增强医疗影像的7大应用场景全面解析
  • 跨技术领域标准规范落地实践(从混乱到统一的架构进化)
  • 独家解密:全球仅3国掌握的6G AI协议兼容性核心技术
  • 量子-经典混合资源分配实战指南(20年专家亲授架构设计秘诀)
  • 量子程序调试难题如何破解?3步实现精准错误定位与修复
  • 【教育量子编程的课程设计】:9所顶尖学校验证有效的教学框架
  • 揭秘协作传感网络中的密钥更新机制:如何实现安全高效的实时加密?
  • 【大规模AI平台稳定性保障】:深度解析云原生环境下的故障检测与切换机制
  • 结构电池预测不准?3步精准定位误差来源并提升模型可靠性
  • 统一技术规范如何赋能企业数字化转型:90%团队忽略的关键路径