我有点困惑,并认为这将是一个简单的答案,但我的搜索并没有帮助我:(我希望能够做一个skt:发送到任何地方。我可以将它发送到OutToUser函数作为一个参数,但我将有很多不同的地方,我想要这样做,并觉得会太乱。我尝试存储类似Server.connections [key] = skt其中key是主机和端口但是当我需要它时,无法弄清楚如何再次获得主机和端口。
有什么好的解决方案吗?
编辑我认为这是一个范围问题,但没有看到一个好的解决方案,因为我是lua的新手。
require "copas"
Server = {}
function Server:new()
local object = {}
setmetatable(object, { __index = Server })
return object
end
function Server:init()
function handler(skt, host, port)
while true do
data = skt:receive()
if data == "quit" then
-- isn't going to work
OutToUser(data)
-- this would work fine of course
-- skt:send(data .. "\r\n")
end
end
end
server = socket.bind("*", 49796)
copas.addserver(server,
function(c) return handler(copas.wrap(c), c:getpeername()) end
)
copas.loop()
end
function OutToUser(data)
skt:send(data .. "\r\n")
end
server = Server:new()
server:init()
答案 0 :(得分:1)
您可以在处理程序的范围内定义OutToUser:
function Server:init()
local function handler(skt, host, port)
--make the function local to here
local function OutToUser(data)
--references the skt variable in the enclosing scope
--(the handler function)
skt:send(data .. "\r\n")
end
while true do
data = skt:receive()
if data == "quit" then
OutToUser(data)
end
end
end
local server = socket.bind("*", 49796)
copas.addserver(server,
function(c) return handler(copas.wrap(c), c:getpeername()) end
)
copas.loop()
end
函数总是可以引用其范围内的变量(函数参数和用local
声明的变量),即使它们离开了该范围 - 您可以将其用作替代解决方案,其中包含< / em>您希望函数在函数外部的作用域中使用的变量:
local function makeOTU(skt)
--skt is visible in the scope of the function
--that gets returned as a result
return function(data)
skt:send(data .. "\r\n")
end
end
function Server:init()
local function handler(skt, host, port)
--create a function that references skt
--as part of its closure
local OutToUser = makeOTU(skt)
while true do
data = skt:receive()
if data == "quit" then
-- OutToUser is still referencing the
-- skt from the call to makeOTU()
OutToUser(data)
end
end
end
local server = socket.bind("*", 49796)
copas.addserver(server,
function(c) return handler(copas.wrap(c), c:getpeername()) end
)
copas.loop()
end
请注意在以下两个示例中使用local
关键字:如果忽略local
,名称将完全忽略范围并进入/来自the global environment(其中只是一个像任何其他表一样的表:当你调用一个新的Lua状态时,它被置于全局_G
)中,这不是你想要的。
将变量保持在其范围的本地而不是使用全局变量非常重要。举例来说,这两个函数:
local function yakkity(file, message)
line = message .. '\n' --without local,
--equivalent to _G["line"] = message
function yak() --without local,
--equivalent to _G["yak"] = function()
file:write(line) --since no local "line" is defined above,
--equivalent to file:write(_G["line"])
end
for i=1, 5 do
yak()
end
end
local function yakker(file, message)
line = message .. '\n' --without local,
--equivalent to _G["line"] = message
return function()
file:write(line) --again, since no local "line" is defined above,
--equivalent to file:write(_G["line"])
end
end
因为他们的变量没有被定义为本地变量,所以他们会破坏彼此的数据,让他们的财物躺在任何人可以滥用它们的地方,并且通常只是像蠢货一样:
--open handles for two files we want:
local yesfile = io.open ("yesyes.txt","w")
local nofile = io.open ("no.txt","w")
--get a function to print "yes!" - or, rather,
--print the value of _G["line"], which we've defined to "yes!".
--We'll see how long that lasts...
local write_yes = yakker(yesfile,"yes!")
--Calling write_yes() now will write "yes!" to our file.
write_yes()
--when we call yakkity, though, it redefines the global value of "line"
--(_G["line"]) - as well as defining its yak() function globally!
--So, while this function call does its job...
yakkity(nofile, "oh no!")
--calling write_yes(), which once again looks up the value of _G["line"],
--now does the exact OPPOSITE of what it's supposed to-
write_yes() --this writes "oh no!" to yesfile!
--additionally, we can still write to the nofile handle we passed to yakkity()
--by calling the globally-defined yak() function!
yak() --this writes a sixth "oh no!" to nofile!
--even once we're done with the file and close our handle to it...
nofile:close()
--yak() still refers to that handle and will still try to write to it!
yak() --tries to write to the closed file handle and throws an error!
答案 1 :(得分:0)
我认为您需要做的就是让OutToUser
函数接受skt参数,并从处理程序内部传递它。