C语言Todo List应用:如何实现文件读取并保存到字符串数组?
待办事项应用的文件读取实现及优化
要解决程序启动后无法读取之前保存的待办列表问题,只需在程序初始化阶段添加文件读取逻辑,同时可以优化现有代码里的小缺陷,让应用更稳定:
一、添加启动时的读取逻辑
在定义完list数组之后,立刻尝试从保存的文件中加载数据:
// 程序启动时加载已保存的待办项 FILE *load_file = fopen("list.bin", "rb"); if (load_file != NULL) { // 直接把文件内容读入数组,长度和数组总大小一致 fread(list, sizeof(char), sizeof(list), load_file); fclose(load_file); } // 如果文件不存在(首次运行),数组保持初始的空状态即可
这里用"rb"二进制模式读取,和保存时的"wb"模式对应,避免不同操作系统下文本模式的格式转换问题,让保存和读取更可靠。
二、修复现有代码的小缺陷
- 删除功能的正确清空方式
原代码用strncpy(list[k-1], " ", 101);只会把第一个字符改成空格,后面的旧内容还留在数组里,应该直接把字符串置空:
// 清空指定位置的待办项,两种方式任选其一 list[k-1][0] = '\0'; // 最简单的方式,直接让字符串长度为0 // 或者用memset清空整个数组元素:memset(list[k-1], 0, MAX_STRING_LENGTH);
- 输入缓冲区的问题处理
添加待办项时,getchar()可能没法完全清空输入缓冲区(比如用户输入数字后多按了几次回车),换成循环清空更稳妥:
case 2: printf("Please enter the number you would like to replace! "); int j; scanf("%d", &j); // 把输入缓冲区里的残留字符(比如回车)全部清掉 while (getchar() != '\n'); scanf("%[^\n]", list[j - 1]); break;
- 保存功能的模式优化
原来的保存用"w"文本模式,改成"wb"二进制模式更合适,避免不必要的格式转换:
if(input == 4){ f = fopen("list.bin", "wb"); if (f != NULL) { fwrite(list, sizeof(char), sizeof(list), f); fclose(f); } printf("Todos saved! Bye~"); return EXIT_SUCCESS; }
三、修改后的完整代码
#include <stdio.h> #include <stdlib.h> #include <string.h> #define MAX_STRING_LENGTH 101 #define MAX_TODO 20 int main() { int input; int loop; FILE *f; char list[MAX_TODO][MAX_STRING_LENGTH] = {}; // 启动时加载已保存的待办列表 FILE *load_file = fopen("list.bin", "rb"); if (load_file != NULL) { fread(list, sizeof(char), sizeof(list), load_file); fclose(load_file); } while(1){ printf("\n==================== ToDo List ====================\n"); printf("Your todos will be saved when you choose option 4!\n"); printf(" - Please enter a number - \n"); printf("1. See todos \n"); printf("2. Add todo \n"); printf("3. Delete todo \n"); printf("4. Leave\n\n"); scanf("%d", &input); if(input == 4){ f = fopen("list.bin", "wb"); if (f != NULL) { fwrite(list, sizeof(char), sizeof(list), f); fclose(f); } printf("Todos saved successfully!"); return EXIT_SUCCESS; }else if (input == 1 || input == 2 || input == 3){ switch(input){ case 1: for (int loop = 0; loop < MAX_TODO; loop++) { printf("[%2d]. %s\n", loop + 1, list[loop]); } break; case 2: printf("Please enter the number you would like to replace! "); int j; scanf("%d", &j); // 清空输入缓冲区 while (getchar() != '\n'); scanf("%[^\n]", list[j - 1]); break; case 3: printf("Please enter the number you would like to remove! "); int k; scanf("%d", &k); // 清空指定位置的待办项 list[k-1][0] = '\0'; printf("[%d] ---> DELETED!!!", k); break; } }else { printf("Please enter 1, 2, 3, or 4...\n"); } } return EXIT_SUCCESS; }
内容的提问来源于stack exchange,提问作者pippin__29
相关产品推荐
相关产品推荐

