【发布时间】:2019-06-06 05:21:07
【问题描述】:
我想知道lua的有什么区别
os.execute('<command>')
和真棒的
awful.spawn('<command>')
我注意到lain suggests 使用os.execute,有什么原因,还是个人喜好问题?
【问题讨论】:
标签: awesome-wm
我想知道lua的有什么区别
os.execute('<command>')
和真棒的
awful.spawn('<command>')
我注意到lain suggests 使用os.execute,有什么原因,还是个人喜好问题?
【问题讨论】:
标签: awesome-wm
永远不要使用os.execute 或io.popen。它们是阻塞函数,导致性能非常差,输入(鼠标/键盘)和客户端重绘延迟显着增加。使用这些函数是一种反模式,只会让一切变得更糟。
查看文档https://awesomewm.org/apidoc/libraries/awful.spawn.html中的警告
现在要真正回答这个问题,您必须了解 Awesome 是单线程的。这意味着它一次只做一件事。如果您拨打os.execute("sleep 10"),您的鼠标将继续移动,但您的计算机将冻结 10 秒。对于执行速度足够快的命令,可能可能会错过这一点,但请记住,由于延迟/频率规则,任何需要 33 毫秒执行的命令最多会丢失 2 帧一个 60fps 的视频游戏(并且将至少丢掉一个)。如果您每秒有很多命令,它们会累加并破坏您的系统性能。
但 Awesome 并不注定要慢。它可能没有多个线程,但它有一个叫做协程的东西,也有回调。这意味着需要时间执行的事情仍然可以在后台执行(使用 C 线程或外部进程 + 套接字)。完成后,他们可以通知 Awesome 线程。这完美地工作并且避免阻塞 Awesome。
现在这将我们带到下一部分。如果我这样做:
-- Do **NOT** do this.
os.execute("sleep 1; echo foo > /tmp/foo.txt")
mylabel.text = io.popen("cat /tmp/foo.txt"):read("*all*")
标签将显示foo。但如果我这样做:
-- Assumes /tmp/foo.txt does not exist
awful.spawn.with_shell("sleep 1; echo foo > /tmp/foo.txt")
mylabel.text = io.popen("cat /tmp/foo.txt"):read("*all*")
那么标签将为空。 awful.spawn 和 awful.spawn.with_shell 将 not 阻塞,因此 io.popen 将在 sleep 1 完成之前执行。这就是为什么我们有异步函数来执行 shell 命令的原因。有许多具有不同特征和复杂性的变体。 awful.spawn.easy_async 是最常见的,因为它对于一般的“我想执行一个命令并在它完成时对输出做一些事情”已经足够了。
awful.spawn.easy_async_with_shell("sleep 1; echo foo > /tmp/foo.txt", function()
awful.spawn.easy_async_with_shell("cat /tmp/foo.txt", function(out)
mylabel.text = out
end)
end)
在此变体中,Awesome 不会阻止。同样,与其他 spawn 一样,您不能在回调函数之外添加代码来使用命令的结果。代码将在命令完成之前执行,因此结果尚不可用。
还有一种叫做协程的东西可以消除对回调的需求,但目前在 Awesome 中很难使用,而且解释起来也很混乱。
【讨论】: