Lua在同一行打印输出

51
在Pascal中,我有writewriteln。显然Lua的print类似于Pascal的writeln。我们是否有类似于Pascal的write的东西?如何让连续的打印命令将它们的输出发送到同一行?
print("Hello")
print("World")

输出:

Hello
world

我想要这个:

Hello world
6个回答

94

使用io.write代替print,因为print仅适用于简单的用法,例如调试等。


15
那就是为什么@lhf是Lua语言的创造者之一。 :) - felipsmartins

26

lhf的正确答案的基础上,io库更适用于生产环境。

基本库中的print函数是作为原始能力实现的。它允许快速而不精确地计算并打印答案,对其显示几乎没有控制。它的主要优点是将所有参数强制转换为string,并使用制表符分隔每个输出参数并提供一个新行。

当需要详细控制输出时,这些优点很快变成了缺陷。因此,您真正需要使用io.write。如果在同一程序中混合使用printio.write,则可能会遇到另一个缺陷。print显式地使用C stdout文件句柄。这意味着,如果您使用io.output更改输出文件句柄,则io.write将按预期执行,但print不会。

一个好的折衷方案是使用io.write实现print的替代方法。它可以看起来像这个未经测试的简单示例,我试图以清晰而不是最佳的方式编写,并仍然正确处理nil参数:

local write = io.write
function print(...)
    local n = select("#",...)
    for i = 1,n do
        local v = tostring(select(i,...))
        write(v)
        if i~=n then write'\t' end
    end
    write'\n'
end

一旦你开始实现自己的print版本,那么很容易为你的应用程序改进它。使用比tostring()提供更多格式控制的工具是一个好主意。另一个考虑的方面是使用除了制表符之外的分隔符。


3
这也可以写成 function print(...) io.write(table.concat({...},"\t"),"\n") end,但这样会创建一个表格并执行连接操作。 - lhf
2
只有当所有参数都是字符串或数字时,才会调用table.concat对表中的每个元素调用lua_isstring()...与基本库print相比,后者确实会在传递每个参数时调用tostring - RBerteig
@Rberteig:为什么你使用select("#",...)而不是只用#arg? - AlexStack
1
arg表是Lua 5.0的一个特性,在5.1中仍然存在但已被弃用,只有在函数中引用时才存在。引用它会导致创建一个新的表,因为...是一个非常特殊的值,不是一个表。此外,即使一些参数是nilselect('#',...)也可以得到正确的长度,而#arg可能不行。 - RBerteig

12
作为一种替代方法,只需构建字符串,然后使用单个print将其输出即可。
您可能并不总是能够访问io库。

如果您没有访问io库的权限,那么为什么会有访问print的权限呢? - Nicol Bolas
11
因为你可能处于嵌入式环境或其他重新定义print函数的受限环境中,例如《魔兽世界》。 - sylvanaar
感谢您的回答。很容易忘记这种方法的存在。 - sgowd

6
您可以使用变量来表示 "Hello" 和 "World"。然后稍后将它们连接起来。像这样:
local h = "Hello"
local w = "World"

print(h..w)

在这种情况下,它将显示为“HelloWorld”。但这很容易解决。希望这有所帮助!

这将分配内存 - 不适合用于打印输出。 - vSzemkel

1

在@Searous的回答基础上,尝试以下操作。

本地变量 h = "hello" 本地变量 w = "world"

打印(h.." "..w)

你可以将它们连接在一起,只需在两个变量之间加上一个空格即可。


0
local h = "Hello"
local w = "World!"

print(h, w)

这将在两个字符串之间输出一个制表符。 - lhf

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接