[Date Prev][Date Next][Thread Prev][Thread Next]
[Date Index]
[Thread Index]
- Subject: Re: [ANN] Lua 5.4.0 (alpha) now available
- From: Sergey Kovalev <kovserg33@...>
- Date: Tue, 16 Jul 2019 00:06:50 +0300
пн, 15 июл. 2019 г. в 23:01, Hisham <h@hisham.hm>:
>
> Have you ever a directory iterator? (e.g. for file in lfs.dir() ) If
> so, you ran into this problem (maybe without realizing it).
lua 5.4 solve this using toclose and 4-th parameter for "for"
print(io.lines"readme.txt")
function: 0x23af370 nil nil file (0x23af130)
> So here's an idea for a third one, let's call it "resource for":
>
> stat ::=
> ...
> for Name ‘=’ exp ‘,’ exp [‘,’ exp] do block end |
> for namelist in explist do block end |
> for namelist ‘=’ exp do block end |
> ...
>
> (as you can see, it is syntactically a mix of the other two: you can
> get multiple names on the LHS but a single expression on the RHS: if
> it uses `=` but no `,`, it's a resource-for). It works in pseudo-code
> like this:
>
> do
> local x, y, ... = exp
> if x == nil and y == nil then break end -- only auto-breaks if
> _all_ values are nil, so we can use libraries which use nil-err
> errors.
> block
> if x then
> local xmt = getmetatable(x)
> if xmt and xmt.__close then
> xmt.__close(x)
> end
> end
> end
>
> Example usage:
>
> for fd, err = io.open("file", "r") do
> if err then
> print("failed!", err)
> break
> end
> print(fd:read("*a"))
> end
I think solution should cover typical usage scenarios. For example
open source and destination files for processing and rise error if it
impossible. "Happy ways" is shorter and simpler to write. Also it
should be able to handle errors by user if he want it.
src=auto(io.close){ io.open(src_filename,"rb") }
dst=auto(io.close){ io.open(dst_filename,"wb") }
-- do somethig with src and dst
> You could read this as a "for that only runs once because it has no
> iteration second argument".
This could be done even now in lua 5.4
-- open.lua
function io_open(name,mode)
local first=true
local f,err=io.open(name,mode)
local close=function() if f then f:close() end f=nil end
return function()
if first then first=false return f or false,err end
end,nil,nil,setmetatable({},{__close=close})
end
for f,err in io_open "readme.txt" do
if not f then warn(err) break end
print(f:read())
end
> if local fd, err = io.open("file", "r") then
> print(fd:read("*a"))
> else
> print("failed!", err)
> end
This is too heavy nested in case of 2 files or if you open an array of
files you have to use recursion. So this is not like it should be.