lua流水账6

一、IO库
1.简单I/O模式
拥有一个当前输入文件和一个当前输出文件,并且提供对这些文件相关的操作。
简单模式的所有操作都是在两个当前文件之上。I/O库将当前输入文件作为标准输入,将当前输出文件作为标准输出。这样当我们执行io.read,就是在标准输入中读取一行。我们可以使用io.input和io.output函数来改变当前文件。例如io.input(filename)就是打开给定文件(以读模式),并将其设置为当前输入文件。接下来所有的输入都来自于该文,直到再次使用io.input。io.output函数。类似于io.input,一旦产生错误两个函数都会产生错误。

io.write("sin(3) = ",math.sin(3),"\n")
io.write(string.format("sin(3) = %.4f\n",math.sin(3)));
输出是:sin(3) = 0.14112000805987
sin(3) = 0.1411

2.在编写代码时应当避免像io.write(a..b..c);这样的书写,这同io.write(a,b,c)的效果是一样的。但是后者因为避免了串联操作,而消耗较少的资源。原则上当你进行粗略编程,或者进行排错时常使用print函数。当需要完全控制输出时使用write。Write函数与print函数不同在于,write不附加任何额外的字符到输出中去,例如制表符,换行符等等。还有write函数是使用当前输出文件,而print始终使用标准输出。另外print函数会自动调用参数的tostring方法,所以可以显示出表函数和nil

```
print("hello","Lua");
print("Hi")
io.write("hello","Lua");
io.write("Hi","\n")
输出是:hello   Lua
Hi
helloLuaHi

3.read函数从当前输入文件读取串,由它的参数控制读取的内容:
(1):”*all”:读取整个文件,io.read(“*all”)函数从当前位置读取整个输入文件。如果当前位置在文件末尾,或者文件为空,函数将返回空串。由于Lua对长串类型值的有效管理,在Lua中使用过滤器的简单方法就是读取整个文件到串中去,处理完之后(例如使用函数gsub),接着写到输出中去。
(2):”*line”:读取下一行,io.read(“*line”)函数返回当前输入文件的下一行(不包含最后的换行符)。当到达文件末尾,返回值为nil(表示没有下一行可返回)。改读取方式是read函数的默认方式,所以可以简写为io.read().通常使用这种方式读取文件是由于对文件的操作是自然逐行进行的,否则更倾向于使用*all一次读取整个文件
(3):”*number”:从串中转换出一个数值,io.read(“*number”)函数从当前输入文件中读取出一个数值。只有在该参数下read函数才返回数值,而不是字符串。当需要从一个文件中读取大量数字时,数字间的字符串为空白可以显著的提高执行性能。*number选项会跳过两个可被识别数字之间的任意空格。如果在当前位置找不到一个数字(由于格式不对,或者是到了文件的结尾),则返回nil可以对每个参数设置选项,函数将返回各自的结果。
(4):num:读取num个字符到串,io.read(num):将尝试从输入文件中读取n个字符。如果无法读取到任何内容(已经到了文件末尾),函数返回nil。否则返回一个最多包含n个字符的串。特别的,io.read(0)函数可以用来测试是否到达了文件末尾。如果不是返回一个空串,如果已是文件末尾返回nil.

t = io.read("*all")
t = string.gsub(t,"([\128-\255=])",function(c)
    return string.format("=%02X",string.byte(c))
end);
io.write(t);
while true do
    local n1,n2,n3 = io.read("*number","*number","*number");
    if not n1 then break end
    print(math.max(n1,n2,n3));
end
输入:6.0 -3.23 15e12
输出:15000000000000
local lines = {}
for line in io.lines() do
    table.insert(lines,line)
end

table.sort(lines);
for i,l in ipairs(lines) do
    io.write(l,"\n")
end

4.完全模式
使用外部的文件句柄来实现。它以一种面向对象的形式,将所有的文件操作定义为文件句柄的方法。该结构类似于C语言中的文件流(FILE*),其呈现了一个打开的文件以及当前存取位置。打开一个文件的函数是io.open。它模仿C语言中的fopen函数,同样需要打开文件的文件名参数,打开模式的字符串参数。
模式字符串可以是”r”(读模式),”w”(写模式,对数据进行覆盖),或者是”a”(附加模式).并且字符”b”可附加在后面表示以二进制形式打开文件。正常情况下open函数返回一个文件的句柄。如果发生错误,则返回nil,以及一个错误信息和错误代码。
同C语言中的流(stream)设定类似,I/O库提供三种预定义的句柄:io.stdin,io.stdout和io.stderr。

local f = assert(io.open(filename,"r"));
local t = f:read("*all");
f:close();
--用如下代码直接发送信息到错误流
io.stderr:write(message)
--使用没有任何参数的io.input()函数得到当前的输入文件句柄
local temp = io.input();
--使用带有参数的io.input(handle)函数设置当前的输入文件为handle句柄代表的输入文件
io.input("newinput");
--关闭当前文件
io.input():close();
--恢复先前文件
io.input(temp);

5.IO优化
由于通常Lua中读取整个文件要比一行一行的读取一个文件快的多。尽管我们有时候针对较大的文件(几十,几百兆),不可能一次把他们读取出来。要处理这样的文件我们仍然可以一段一段(例如8kb一段)的读取它们。

local BUFSIZE = 2^13
local f = io.input(arg[1]);
local cc,lc,wc = 0,0,0
while true do
--为了避免切割文件中的行,加入下述代码,其中rest就保存了任何可能被段划分切断的行
--然后再将段(chunk)和行连接起来。这样每个段就是以一个完整的行结尾的了。
    local lines,rest = f:read(BUFSIZE,"*line");
    if not lines then break end
    if rest then lines = lines..rest..'\n' end
    cc = cc + string.len(lines);
    local _,t = string.gsub(lines,"%S+","");
    wc = wc + t;
    _,t = string.gsub(lines,"\n","\n");
    lc = lc + t;
end
print(lc,wc,cc);

6.默认的简单模式总是以文本模式打开,在Unix中二进制文件和文本文件并没有区别,但是在如Windows这样的系统中,二进制文件必须以显式的标记来打开文件。控制这样的二进制文件,你必须将”b”标记添加在io.open函数的格式字符串参数中。在Lua中二进制文件的控制和文本类似。一个串可以包含任何字节值,库中几乎所有的函数都可以用来处理任意字节值。(你甚至可以对二进制的“串”进行模式比较,只要串中不存在0值。如果想要进行0值字节的匹配,你可以使用%z代替)这样使用*all模式就是读取整个文件的值,使用数字n就是读取n个字节的值。

local inp = assert(io.open(arg[1],"rb"));
local out = assert(io.open(arg[2],"wb"));
local data = inp:read("*all");
--将文本文件从DOS模式转换到Unix模式,即将回车换行符替换成换行符
data = string.gsub(data,"\r\n","\n");
out:write(data)
assert(out:close());
--该程序对二进制文件进行一次值分析。程序的第一个参数是输入文件名,输出为标准输出。其按照10字节为一段读取文件,将每一段
--各字节的十六进制表示显示出来。接着再以文本的形式写出该段,并将控制字符转换为点号。
local f = assert(io.open(arg[1],"rb"));
local block = 10;
while true do
    local bytes = f:read(block);
    if not bytes then break end
    for b in string.gfind(bytes,".") do
        io.write(string.format("%02X ",string.byte(b)))
    end
    io.write(string.rep("  ",block-string.len(bytes) + 1));
    io.write(string.gsub(bytes,"%c","."),"\n");
end

7.函数tmpfile函数用来返回临时文件的句柄,并且其打开模式为read/write模式。该临时文件在程序执行完后会自动进行清除。函数flush用来应用针对文件的所有修改。同write函数一样,该函数的调用既可以按函数调用的方法使用io.flush()来应用当前输出文件;也可以按文件句柄方法的样式f:flush()来应用文件f.函数seek用来得到和设置一个文件的当前存取位置。它的一般形式为filehandle:seek(whence,offset)。
Whence参数是一个表示偏移方式的字符串。它可以是”set”,偏移值是从文件头开始的;”cur”,偏移值从当前位置开始;”end”,偏移值从文件尾往前计数。offset即为偏移的数值,由whence的值和offset相结合得到新的文件读取位置。该位置是实际从文件开头计数的字节数。whence的默认值为”cur”,offset的默认值为0。这样调用file:seek()得到的返回值就是文件当前的存取位置,且保持不变。file:seek(“set”)就是将文件的存取位置重设到文件开头。(返回值当然是0)。而file:seek(“end”)就是将位置设为文件尾,同时就可以得到文件的大小。

function fsize(file)
    local current = file:seek();
    local size = file:seek("end");
    file:seek("set",current);
    return size;
end
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
VC6是微软公司开发的一款集成开发环境(IDE),用于C++编程。而Lua是一种轻巧的脚本语言,可用于嵌入其他程序中。将VC6与Lua集成,可以让开发者在VC6环境中通过Lua脚本来编写部分逻辑,以实现更灵活的功能。 实现VC6与Lua的集成,需要以下几个步骤: 1. 下载并安装Lua库:在Lua官方网站上下载适用于VC6的Lua库,并按照官方指导进行安装。 2. 配置环境变量:将Lua库的路径添加到VC6的环境变量配置中,这样VC6就能够找到Lua库并进行调用。 3. 添加Lua的头文件和库文件:在VC6的项目中,添加Lua库的头文件和库文件路径,以便于在代码中引用和链接。 4. 编写代码:在VC6的代码中,通过引入Lua的头文件,可以使用Lua提供的API来执行Lua脚本,调用Lua函数等操作。 5. 构建与调试:编译和构建项目,并进行调试,确保集成的Lua代码能够正确执行,并与C++代码进行交互。 通过VC6与Lua的集成,可以在VC6的开发环境中使用Lua作为脚本语言,实现更灵活、动态的功能。例如,可以将一些频繁变化的逻辑放在Lua脚本中,而不用每次修改C++代码并重新编译;还可以利用Lua强大的脚本功能来进行模块化开发,提高代码的可维护性和重用性。 需要注意的是,由于VC6是较旧的开发环境,可能与较新版本的Lua库存在兼容性问题。因此,在集成VC6与Lua时,需要选择适用于VC6的Lua库,并仔细遵循官方的安装和配置指南。同时,也建议尽量使用更新的开发环境和工具链,以获得更好的开发体验和技术支持。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值