Lua IO库详解

I/O 库提供了两套不同风格的文件处理接口。 第一种风格使用隐式的文件句柄; 它提供设置默认输入文件及默认输出文件的操作, 所有的输入输出操作都针对这些默认文件。 第二种风格使用显式的文件句柄。

当使用隐式文件句柄时, 所有的操作都由表 io 提供。 若使用显式文件句柄, io.open 会返回一个文件句柄,且所有的操作都由该文件句柄的方法来提供。

表 io 中也提供了三个 和 C 中含义相同的预定义文件句柄: io.stdin io.stdout io.stderr。 I/O 库永远不会关闭这些文件。

除非另有说明, I/O 函数在出错时都返回 nil (第二个返回值为错误消息,第三个返回值为系统相关的错误码)。 成功时返回与 nil 不同的值

io:open(filename [, mode])

这个函数用字符串 mode 指定的模式打开一个文件。 返回新的文件句柄。 当出错时,返回 nil 加错误消息。
mode 字符串可以是下列任意值:

  • **"r": **只读模式,这也是对已存在的文件的默认打开模式。
  • **"w": **可写模式,允许修改已经存在的文件和创建新文件(不可读)。
  • **"a": **追加模式,对于已存的文件允许追加新内容,但不允许修改原有内容,同时也可以创建新文件。
  • **"r+": **读写模式打开已存的在文件。
  • **"w+": **如果文件已存在则删除文件中数据;若文件不存在则新建文件。读写模式打开。
  • **"a+": **以可读的追加模式打开已存在文件,若文件不存在则新建文件。

mode 字符串可以在最后加一个 'b' , 这会在某些系统上以二进制方式打开文件。

当文件不存在时

local file = io.open("./test.txt")
file:close()

模式"r","r+",会提示错误,这两种模式不会自动创建为难。
模式"a","a+","w","w+"都会创建文件

当文件存在时
原文件:

test.txt
this is test 1
this is test 2

lua文件:

local file = io.open("./test.txt", mode)
print(file:write("123", "a"))
file:close()

local file = io.open("./test.txt", "r+")
print(file:read("*a"))
file:close()

对不同模式,分别调用读写操作

mode为"r"
Output:
写:
nil Bad file descriptor 9

文件可读,不可写

mode为"r+"
Output :
true

文件内容:
123a is test 1
this is test 2

文件内容保留,新内容从文件头输入
可读

mode为"w"
Output :
true

文件内容:
123a

读:
nil No error    0

用输入内容覆盖文件内容
使用"w"模式打开文件时,会立即删除文件内容,即使不写入内容.
用"w"模式读时,返回nil

mode为"w+"
Output:
true

文件内容:
123a

用输入内容覆盖文件内容
使用"w+"模式打开文件时,会立即删除文件内容
用"w+"模式读时,返回空字符串

mode为"a"
Output:
true

文件内容:
this is test 1
this is test 2123a

读:
nil No error    0

追加模式写入
不可读

mode为"a+"
Output:
true

文件内容:
this is test 1
this is test 2123a

追加模式写入
可读


io:input([file])

用文件名调用它时,(以文本模式)来打开该名字的文件, 并将文件句柄设为默认输入文件。 如果用文件句柄去调用它, 就简单的将该句柄设为默认输入文件。 如果调用时不传参数,它返回当前的默认输入文件。
在出错的情况下,函数抛出错误而不是返回错误码。

--文件名
io.input("./test.txt")
print(io.read("*a"))
io:close()

Output:
this is test 1
this is test 2

--文件句柄(需要使用可读模式)
local file = io.open("./test.txt", "r")
print(io.input(file))
print(io.read("*a"))
print(file)
io.close()

Output:
file (777E1BD8)
this is test 1
this is test 2
file (777E1BD8

io:output([file])

用文件名调用它时,(以文本模式)来打开该名字的文件, 并将文件句柄设为默认输出文件。 如果用文件句柄去调用它, 就简单的将该句柄设为默认输出文件。 如果调用时不传参数,它返回当前的默认输出文件。
在出错的情况下,函数抛出错误而不是返回错误码。

print(io.output("./test.txt"))
io.write("123")
io.close()

Output:
file (777E1BD8)

文件内容:
123

io.popen (prog [, mode])

这个函数和系统有关,不是所有的平台都提供。

用一个分离进程开启程序 prog, 返回的文件句柄可用于从这个程序中读取数据 (如果 mode 为 "r",这是默认值) 或是向这个程序写入输入(当 mode 为 "w" 时)。


io.tmpfile()

返回一个临时文件的句柄。 这个文件以更新模式打开,在程序结束时会自动删除。


io.type(obj)

检查 obj 是否是合法的文件句柄。 如果 obj 它是一个打开的文件句柄,返回字符串 "file"。 如果 obj 是一个关闭的文件句柄,返回字符串 "closed file"。 如果 obj 不是文件句柄,返回 nil

local file = io.tmpfile()
print(io.type(file))
file:close()
print(io.type(file))
print(io.type({}))

Output:
file
closed file
nil

io.lines([filename])

提供一个循环迭代器以遍历文件,如果指定了文件名则当遍历结束后将自动关闭该文件;若使用默认文件,则遍历结束后不会自动关闭文件。

for line in io.lines("./test.txt") do
    print(line)
end

Output:
this is test 1
this is test 2

注:Lua 5.3 有变动,添加模式数


file:lines()

返回一个迭代器函数, 每次调用迭代器时,都从文件中取一行数据,和 io.lines 不同, 这个函数在循环结束后不会关闭文件。
注:Lua 5.3 有变动,添加模式数


file:read(...)

读文件 file, 指定的格式决定了要读什么。 对于每种格式,函数返回读出的字符对应的字符串或数字。 若不能以该格式对应读出数据则返回 nil。 (对于最后这种情况, 函数不会读出后续的格式。) 当调用时不传格式,它会使用默认格式读下一行

  • *"n": ** 从文件当前位置读入一个数字,如果该位置不为数字则返回 nil。
  • *"l": ** 读入当前行。
  • *"a": ** 读入从当前文件指针位置开始的整个文件内容。
  • number: 读入指定字节数的内容。
local file = io.open("./test.txt", "r")
print(file:read("*l"))
print(file:read("*n"))
print(file:read(2))

Output:
this is test 1
nil
th

注:Lua 5.3 有变动,去掉*号,并添加"i"和"L"格式


io:read(...)

等价于 io.input():read(···)。


file:write(...)

将参数的值逐个写入 file。 参数必须是字符串或数字。
成功时,函数返回 file。 否则返回 nil 加错误描述字符串。


io:write(...)

等价于 io.output():write(···)。


file:close()

关闭 file。 注意,文件在句柄被垃圾回收时会自动关闭, 但是多久以后发生,时间不可预期的。


io:close()

等价于 file:close()。 不给出 file 时将关闭默认输出文件。


file:flush()

将写入的数据保存到 file 中


io:flush()

等价于 io.output():flush()。


file:seek([whence [, offset]])

设置及获取基于文件开头处计算出的位置。 设置的位置由 offset 和 whence 字符串 whence 指定的基点决定。基点可以是:

  • **"set": **基点为 0 (文件开头);
  • **"cur": **基点为当前位置了;
  • **"end": **基点为文件尾;

当 seek 成功时,返回最终从文件开头计算起的文件的位置。 当 seek 失败时,返回 nil 加上一个错误描述字符串。

whence 的默认值是 "cur", offset 默认为 0 。 因此,调用 file:seek() 可以返回文件当前位置,并不改变它; 调用 file:seek("set") 将位置设为文件开头(并返回 0); 调用 file:seek("end") 将位置设到文件末尾,并返回文件大小。

local file = io.open("./test.txt", "r+")
print(file:seek("end"))
print(file:seek("set"))
print(file:seek())
print(file:seek("cur", 10))
print(file:seek("cur"))
print(file:read(1))
print(file:seek("cur"))
file:write("123")
file:close()

Output:
30
0
0
10
10
s
11

修改文件的值会影响read操作 以及以"r+"模式打开文件的write操作

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 196,264评论 5 462
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 82,549评论 2 373
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 143,389评论 0 325
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 52,616评论 1 267
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 61,461评论 5 358
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 46,351评论 1 273
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 36,776评论 3 387
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 35,414评论 0 255
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 39,722评论 1 294
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 34,760评论 2 314
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 36,537评论 1 326
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,381评论 3 315
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 37,787评论 3 300
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,030评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,304评论 1 252
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 41,734评论 2 342
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 40,943评论 2 336

推荐阅读更多精彩内容