好的,所以我正在写游戏,在这个游戏中,有一个交互式设置菜单。我想要做的是写入文件(如果它不存在),如果文件读取,则从文件中读取,应用文件中指定的设置,并使用用户选择的新设置覆盖它,如果用户选择更改设置。所以它会像这样(psuedo-code):
if (file does not exist)
write_defaults
open settings
read from file
apply settings specified in file
while (user is changing settings)
if (user is done) break
write new settings to file
apply new settings
现在我将用于fopen的第二个参数?我已尝试过“r +”和“w +”,但我遇到了两个问题。
答案 0 :(得分:2)
我将以"w"
打开写操作,并以"r"
重新打开读取操作,除非您正在进行某种随机访问同时读/写。
正如@stefan在下面的评论中提到的,如果您正在处理原始二进制数据而不是文本,则需要"rb"
或"wb"
。
答案 1 :(得分:0)
使用"r+"
对于第一次尝试是正确的;如果由于文件不存在而失败,请再次使用"w+"
。这会为您提供一个可供更新的文件,但如果该文件已存在,则不会破坏该文件。
但是,如果在使用"r+"
的失败打开和使用{{成功打开之间创建文件 - 存在TOCTOU(检查时间,使用时间)漏洞,则这是次优的。 1}},文件中的信息将丢失。
如果您可以访问POSIX函数,则可以使用"w+"
而不是open()
在一次原子尝试中正确完成工作,然后fopen()
将文件描述符转换为文件流。
fdopen()
这样做的一个缺点是它将通过破坏的符号链接创建一个文件。您可以使用FILE *carefully_open(const char *file)
{
int fd = open(file, O_RDWR | O_CREAT, 0644);
FILE *fp = 0;
if (fd >= 0)
fp = fdopen(fd, "r+");
if (fd >= 0 && fp == 0)
close(fd);
return fp;
}
标志来避免这种情况,但如果文件存在则打开将失败。毕竟,您最终拨打了O_EXCL
两个电话,其中一个只有open()
而第二个只有O_RDRW
,以防止出现损坏的符号。
(什么是损坏的符号链接?如果当前目录中没有文件O_RDRW | O_CREAT | O_EXCL
,pqr
表示ln -s ./pqr xyz
是一个损坏的符号链接,将通过创建文件来“修复”显示xyz
调用的'pqr'。)
你有什么问题?
答案 2 :(得分:0)
只需用“r +”打开文件即可。检查返回的指针,如果指针不为NULL,则从文件中读取设置。然后写入文件。