大家好,我是袁庭新。
文件I/O(Input/Output)操作在Lua中用于与外部文件进行交互,包括读取文件中的数据和将数据写入文件。Lua提供了两种模式来进行文件操作:简单模式和完全模式。下面将详细介绍这两种模式的基本使用。
1.简单模式
1.1 简单模式介绍
简单模式提供了基本的文件操作功能,它主要通过io.open函数打开文件,然后使用返回的文件句柄进行读取和写入操作。这种模式的操作相对比较直接,适合处理简单的文件I/O需求。
简单模式的特点是,操作函数较为直观,容易理解和使用。对于小型文件的读取和写入操作比较方便。常见的使用场景是,程序的配置文件读取,我们可以使用简单模式以只读方式打开某个文件(如config.properties),逐行读取并解析这些配置参数。
1.2 函数介绍
io.open函数用于打开文件并返回一个文件描述符。如果打开失败,则返回nil加上错误消息。打开文件操作语句如下:
file = io.open(filename [, mode])
在上述语句中,filename参数表示要打开的文件的名称,可以包含路径。如果只给出文件名,默认在当前目录下查找文件。mode参数表示文件打开模式,有以下几种常见选项:
模式 | 描述 |
---|---|
r | 以只读方式打开文件。文件必须存在,否则会出错。 |
w | 以写入方式打开文件。如果文件存在,会清空文件内容;如果文件不存在,则创建新文件。 |
a | 以追加方式打开文件。如果文件存在,新写入的数据会添加在文件末尾;如果文件不存在,则创建新文件。 |
r+ | 以读写方式打开文件。文件必须存在,读取和写入操作都可以进行。 |
w+ | 打开可读写文件,若文件存在则文件长度清为零,即该文件内容会消失;若文件不存在则创建该文件。 |
a+ | 文件以追加模式打开,同时允许读取文件内容。即此文件可读可写。 |
b | 以二进制模式打开文件(可以与其他模式组合使用,如"rb"表示二进制读,"wb"表示二进制写) |
io.read([format])函数表示从默认输入文件中读取数据,根据给定的模式读取不同类型的值。该函数的参数可以是下表中的一个。
模式 | 描述 |
---|---|
"*l" | 默认参数,读取一行,在文件尾(EOF)处返回nil。例:file.read("*l")。 |
"*n" | 读取一个数字并返回它。例:file.read("*n")。 |
"*a" | 从当前位置读取整个文件。例:file.read("*a")。 |
number | 返回一个指定字符个数的字符串,或在EOF时返回nil。例:file.read(5)。 |
I/O简单模式操作的其他常用函数介绍见下表:
函数 | 含义 |
---|---|
io.input([file]) | 如果给出参数file,则将其设置为新的默认输入文件;如果没有给出参数,则返回当前的默认输入文件。 |
io.output([file]) | 用于设置或获取默认输出文件。 |
io.write(...) | 向默认输出文件写入数据,可以是字符串或其他可以转换成字符串的值。 |
io.close([file]) | 关闭文件。如果没有给出参数,则关闭默认输出文件。 |
io.flush() | 强制刷新输出缓冲区,确保所有数据都被写入文件。 |
io.tmpfile() | 用于创建一个临时文件,并返回一个与该文件关联的文件句柄。这个临时文件在程序结束时(或者文件被显式关闭时)会自动删除,因此非常适合用于需要短暂存储数据的场景。 |
io.type(file) | 用于检查一个文件句柄(file handle)或文件对象的类型。具体来说,它可以识别一个文件对象是以何种模式打开的,比如读模式、写模式或追加模式等。 |
1.3 示例演示
这里需要提前创建准备好两个文件——input.txt和output.txt。并在input.txt文件中添加如下的内容:
文件第一行内容...
文件第二行内容...
文件第三行内容...
然后创建一个名为simple_model_test.lua的脚本文件,并在该文件中添加如下的内容。
-- simple_model_test.lua文件
-- 打开文件并设置为当前输入文件
local inputFile = io.open("input.txt", "r")
io.input(inputFile)
-- 读取一行并打印
local line = io.read("*l")
print(line)
-- 关闭输入文件
io.close(inputFile)
-- 打开文件并设置为当前输出文件
local outputFile = io.open("output.txt", "w")
io.output(outputFile)
-- 写入一行
io.write("Hello, Lua!\n")
-- 关闭输出文件
io.close(outputFile)
执行以上脚本代码,程序输出结果如下。
文件第一行内容...
然后通过"cat output.txt"命令查看该文件的内容,输入结果如下所示。
Hello, Lua!
简单模式在做一些简单的文件操作时较为合适。但是在进行一些高级的文件操作的时候,简单模式就显得力不从心。例如同时读取多个文件这样的操作,使用完全模式则较为合适。
2.完全模式
2.1 完全模式介绍
在Lua中,文件I/O的完全模式是一种更为灵活和强大的文件操作方式。它提供了一系列功能,用于更精细地控制文件输入/输出流,包括对默认输入输出流的设置、高效的逐行读取以及文件内部位置的精确控制等操作,相较于简单模式,能满足更复杂的文件处理需求。
完全模式通过文件对象(由io.open()返回),可以直接调用更多函数进行复杂的文件操作,并且可以更好地控制文件访问。
2.2 函数介绍
I/O完全模式操作的常用函数介绍见下表:
函数 | 含义 |
---|---|
io.open(filename [, mode]) | 与简单模式中的io.open相同,打开一个文件并返回一个文件句柄。 |
file:read([format]) | 读取文件内容。format参数与io.read相同。 |
file:write(...) | 向文件写入数据。 |
file:flush() | 将所有已缓冲的数据写入文件。 |
file:close() | 关闭文件。 |
file:setvbuf(mode [, size]) | 设置文件的缓冲方式,对于提高性能非常重要。 |
io.lines(filename) | 用于逐行读取文件的内容,并返回一个迭代器函数。每次调用迭代器函数将返回文件中的一行内容,直到文件末尾。参数filename是一个字符串,表示要读取的文件的路径。 |
函数file:seek([whence, [offset]])用于对已经打开的文件进行定位操作。
- whence参数指定定位的参考点,有以下几种选项:
- "set":从文件开头开始定位,offset是相对于文件开头的偏移量。例如,若执行file:seek("set", 5),文件指针会被定位到文件开头后的第5个字节位置。
- "cur":从当前位置开始定位,offset是相对于当前位置的偏移量。如果offset为正数,指针向后移动;如果为负数,指针向前移动。比如,当前文件指针在第10个字节位置,执行file:seek("cur", 3)后,指针会移动到第13个字节位置。
- "end":从文件末尾开始定位,offset是相对于文件末尾的偏移量(偏移量为负数时表示向前移动)。例如,执行file:seek("end", -2)会将文件指针定位到文件末尾前2个字节的位置。
- offset参数默认为0。这个函数返回文件指针的新位置(以字节为单位),如果发生错误则返回nil。
2.3 示例演示
创建一个名为complete_model_test.lua的脚本文件,并在该文件中添加如下的内容。
-- complete_model_test.lua文件
-- 打开文件进行读写操作
local file, err = io.open("example.txt", "w+")
if not file then error("无法打开文件:" .. err) end
-- 写入几行数据
file:write("Line 1\n")
file:write("Line 2\n")
file:write("Line 3\n")
-- 将文件指针设置到文件头
file:seek("set", 0)
-- 逐行读取并打印文件内容
for line in file:lines() do
print(line)
end
-- 关闭文件
file:close()
-- 以附加模式打开文件并写入数据
local appendFile = io.open("example.txt", "a")
appendFile:write("Line 4\n")
appendFile:close()
-- 重新打开文件并读取所有数据
local readFile = io.open("example.txt", "r")
local content = readFile:read("*a")
print(content)
readFile:close()
执行以上脚本代码,程序输出结果如下。
Line 1
Line 2
Line 3
Line 1
Line 2
Line 3
Line 4
3.总结
本文主要讲述了 Lua 语言中的文件 I/O 操作,包括简单模式和完全模式。
简单模式通过 io.open 打开文件,其 mode 有 r、w、a 等多种,分别对应只读、写入、追加等操作,还可组合 b 用于二进制。io.read 能按不同格式读取数据,如 *l 读一行。此外还有 io.input 等一系列函数用于设置输入输出、写入、关闭、刷新缓冲区、创建临时文件和检查文件类型等操作,适用于小型文件和配置文件读取等简单场景。
完全模式更为强大灵活,同样用 io.open 返回文件对象后可调用更多函数。file:write 写入数据,file:flush 刷新,file:close 关闭,file:setvbuf 可设置缓冲提升性能,io.lines 逐行读取返回迭代器。file:seek 可精确控制文件指针位置,通过 whence 指定参考点,offset 设偏移量。在示例中对 example.txt 进行了创建、写入、定位、读取和追加数据等操作,能满足如同时读取多个文件等复杂的文件处理需求,相比简单模式在高级操作上更具优势。