Lua在莫斯科2019:采访Roberto Ierusalimschy



前一段时间,Lua编程语言的创建者Roberto Ierusalimschy访问了我们的莫斯科办事处。 我们还问了他一些在Habr.com用户参与下准备的问题。 最后,我们想分享这次采访的全文。

-让我们从一些哲学问题开始。 想象一下,如果您从头开始重新创建Lua,那么您将在Lua中更改哪三件事?

-哇! 这是一个难题。 在语言的创建和开发中嵌入了太多的历史。 这不是一次重大的决定。 有一些遗憾,这些年来我有机会纠正了其中的一些遗憾。 人们总是因为兼容性而抱怨。 我们做了几次。 我只是在想小事情。

-默认为全局? 您认为这是这样吗?

-也许吧。 但是对于动态语言来说这非常困难。 也许解决方案将是完全没有默认值,但是那时将很难使用变量。

例如,您将不得不以某种方式声明所有标准库。 您需要单线print(sin(x)) ,然后您必须声明'print'并且还声明'sin'。 因此,对于这种非常短的脚本进行声明有点奇怪。

我认为,任何较大的值都应该没有默认值。 默认情况下不是本地解决方案,它不存在。 它仅用于分配,不用于使用。 我们分配了一些东西,然后我们先使用再分配,这存在一些错误-完全令人迷惑。

也许默认情况下的全局不是完美的,但是可以肯定的是默认情况下的本地不是解决方案。 我认为是某种声明,也许是可选声明...我们已经多次提出该提案-某种全局声明。 但最终,我认为问题在于人们开始要求越来越多,而我们却放弃了。

(讽刺地)是的,我们将提出一些全球性声明-加上那个,那个,那个,最后,我们了解最终结论将无法满足大多数人的需求,我们也不会提出所有人想要的所有选择,所以我们什么都不要放 最后,严格模式是一个合理的折衷方案。

这是一个问题:例如,我们经常在模块内部使用字段,那么您再次遇到相同的问题。 这只是一般解决方案可能包含的错误的一种非常特殊的情况。 因此,我认为,如果您确实希望这样做,则应使用静态类型的语言。

-默认情况下,全局也适用于小型配置文件。

-是的,确切地说,适用于小型脚本等。

-这里没有权衡?

-不,总会有取舍。 在小脚本和真实程序之间或类似的东西之间要权衡。

-因此,我们回到第一个大问题:如果有机会,您将改变三件事。 如我所见,您对我们现在拥有的产品感到非常满意,对吗?

-好吧,这不是什么大的变化,但是...我们变成了大变化的坏帐是零钱。 我真的很后悔。 我做了那种实现,一种骇客……你知道我做了什么吗? 我发送了大约六个月或一年以前的Lua版本,该版本的表中没有任何内容。

-没有值?

没错 我认为它在表中称为nils-称为null。 我们在语法上做了一些改动,以使其在某种程度上兼容。

-为什么需要?

-我真的相信这是一个完整的漏洞问题...我认为,如果我们可以使用[表中的nil],则数组中nil的大多数问题都将消失... ...因为确切的问题不是数组中的nil。 人们说我们不能在数组中使用零,因此我们应该将数组与表分开。 但是真正的问题是我们不能在表中有nil! 因此,问题出在表上,而不是我们表示数组的方式。 如果我们可以在表中使用nil,那么我们将在数组中使用nil,而无需其他任何操作。 因此,我对此感到非常遗憾,而且许多人不了解,如果Lua允许在表中使用nil,事情将会如何变化。

-我可以告诉你一个有关Tarantool的故事吗? 实际上,我们有自己的null实现,它是null指针的CDATA。 我们在需要内存空间的地方使用它。 在进行远程调用等时填充位置参数。 但是我们通常会受此困扰,因为CDATA始终会转换为“ true”。 因此,数组中的nils可以解决很多问题。

-是的,我知道。 这正是我的观点-这将为很多人解决很多问题,但是兼容性存在很大的问题。 我们没有能力发布如此不兼容的版本,然后破坏社区,并为Lua 5和Lua 6等提供了不同的文档。 但是也许有一天我们会发布它。 但这是一个很大的变化。 我认为从一开始就应该是这样-如果是这样,除了兼容性之外,这将是该语言的一个小改变。 它以非常微妙的方式破坏了许多程序。

-除了兼容性以外还有什么缺点?

-除了兼容性之外,缺点是我们需要两个新操作,两个新功能。 就像“删除键”一样,因为分配nil不会删除键,所以我们将有一种原始操作来删除键并将其真正从表中删除。 和“测试”来检查准确区分零和缺席的位置。 因此,我们需要两个原始函数。

-您是否分析了这对实际实施的影响?

-是的,我们发布了Lua版本。 正如我所说,它以许多微妙的方式破坏了代码。 有人在做table.insert(f(x))-对函数的调用。 它是有意设计的,当一个函数不想插入任何东西时,它返回nil。 因此,而不是单独检查“是否要插入?”,然后调用table.insert,并知道如果它为nil,则不会插入它。 当每种语言的所有内容都成为一个功能时,就会出现错误,并且人们会使用该功能-但是,如果更改它,则会破坏代码。

-新的void类型呢? 像零,但无效?

-哦,不,这是一场噩梦。 您只是推迟了问题,如果您提出另一个问题,那么您将需要另一个问题。 那不是解决方案。 主要问题(不是主要问题,而是主要问题之一)是在该语言的许多地方都已经扎根了nil。 例如,一个非常典型的例子。 我们说:您应该避免在数组,孔中使用nil。 但是然后我们有了返回nil以及nil之后的函数,因此我们得到一个错误代码。 这样,构造本身就假设nil代表什么……例如,如果我要列出该函数的返回值列表,则只是要捕获所有这些返回值。

-这就是为什么要这么做。 :)

-的确如此,但是您不必为了如此原始而显而易见的问题而使用hack。 但是库的构建方式……我曾经想到过-也许库应该返回false而不是nil-但这是半熟的解决方案,它只能解决一小部分问题。 就像我说的那样,真正的问题是表中应该有nil。 如果没有,也许我们不应该像现在这样频繁地使用nils。 都有些混乱。 因此,如果创建一个void,这些函数仍将返回nil,除非创建新类型并且这些函数将返回void而不是nil,否则我们仍然会遇到此问题。

-Void可用于显式告知该键应保留在表中-具有void值的键。 而且nil可以像以前一样行动。

-是的,这就是我的意思。 库中的所有函数应返回void或nil。

-他们仍然可以返回nil,为什么不呢?

-因为我们仍然会遇到无法捕获某些功能的问题。

-但是不会有第一把钥匙,只有第二把钥匙。

-不,不会有第二个键,因为计数将是错误的,并且阵列中将有一个孔。

-是的,所以您是说您需要一种错误的元方法吗?

-是的 我的梦想是这样的:

{f(x)}

您应该捕获函数f(x)所有返回值。 然后我可以执行%x#x ,这将给我函数返回的次数。 那就是合理的语言应该做的。 因此,除非我们有一个很强的规则,即函数永远不应该返回nil,否则创建一个void并不能解决这个问题,但是为什么我们需要nil? 也许我们应该避免它。

-Roberto,Lua会提供更强大的静态分析支持吗? 就像“ Lua检查类固醇”。 我知道这当然不会解决所有问题。 您是说这是6.0的功能,对吧? 因此,如果在5.x中有一个强大的静态分析工具-如果投入了工时和工年,这真的有帮助吗?

-不,我认为一种非常强大的静态分析工具称为...类型系统! 如果您想要一个真正强大的工具,则应该使用静态类型的语言,例如Haskell甚至具有依赖类型的语言。 然后,您将拥有真正强大的分析工具。

-但是你没有Lua。

-确实,Lua是为了...

-不精确? 我非常喜欢您的长颈鹿关于静态和动态类型的图片。

-是的,我的最后一张幻灯片。


Roberto Ierusalimschy的演讲的最后一张幻灯片“为什么(为什么不是)Lua?”
在莫斯科的Lua 2019会议上

-关于下一个准备好的问题,让我们回到这张照片。 如果我做对了,您的立场是Lua是用于解决不太大的任务的小型便捷工具。

-不,我认为您可以完成一些大任务,但不能进行静态分析。 我坚信测试。 顺便说一句,我不同意覆盖率,您的意见是我们不应该追求覆盖率。我的意思是,我完全同意覆盖率并不意味着全面测试,但是未覆盖率意味着测试率为零。 因此,我谈到了一个测试室-您在斯德哥尔摩。 因此,我从[几个]错误开始了我的测试-这是最奇怪的事情-其中一个很出名,另一个完全不出名。 在Microsoft,C和C ++的头文件中,它完全被破坏了。 因此,我在网上搜索,没有人关心它,甚至没有注意到它。

例如,有一个数学函数modf() ,您必须传递一个指向double的指针,因为它返回了两个double。 我们翻译数字的整数部分或小数部分。 因此,这很长一段时间以来一直是标准库的一部分。 然后是C 99,您需要此函数进行浮点运算。 Microsoft的头文件只是保留了此功能,并声明了另一个宏。 因此,这使它成为类型转换。 因此,它将double强制转换为float,然后将其强制转换为double,以使指针浮动

-这张图片有问题。

-这是Visual C ++和Visual C 2007的头文件。我的意思是,如果使用任何参数一次调用此函数,然后检查结果-除非为零,否则将是错误的。 否则,任何其他值将是错误的。 您将永远不会使用此功能。 零覆盖。 然后,关于测试的讨论很多。我的意思是,只调用一次函数,检查结果! 所以它在那里,已经存在了很长一段时间,多年来一直没人在意。 一个非常有名的是在苹果公司。 诸如if… what… goto… ok ”之类的东西。 有人在这里发表另一句话。 然后一切都会好起来的。 并且有很多讨论,您应该有规则,方括号应该是您样式中必需的,等等。 没有人提到这里还有很多其他的假设。 那从来没有执行过...

-据我所记得,还有一个安全问题。

-是的。 因为他们只是测试批准的案例。 他们没有测试任何东西,因为一切都会被批准。 这意味着安全应用程序中没有一个测试用例可以检查它是否拒绝某些连接或应该拒绝的连接。 因此,每个人都讨论并说他们应该有括号...他们应该有测试,最低测试! 因为没有人测试过,所以这就是我所指的范围。 人们不做基础测试,这真是令人难以置信。 因为如果他们正在执行所有基本测试,那么当然,进行所有覆盖并执行所有行等都是噩梦。 人们甚至忽略了基本测试,因此覆盖率至少约为最小值。 这是一种将注意力吸引到您忘记的程序某些部分的方法。 它是有关如何稍微改善测试的一种指南。

-Tarantool的测试范围是什么? 83%! Roberto,Lua的测试范围是什么?

-大约99.6。 您有几行代码? 一百万,几十万? 这些是巨大的数字。 十万分之一的内容是一千行未经测试的代码。 您根本没有执行它。 您的用户没有进行任何测试。

-那么有大约17%的Tarantool功能当前未使用?

-我不确定您是否要将所有内容都放回原处...我认为动态语言(和静态语言)的问题之一是人们没有测试内容。 即使您使用的是静态语言,除非您有某种证明系统(即使不是Haskell,而是Coq),也要为此进行更改。 没有静态分析工具可以捕获这些错误,因此您确实需要测试。 如果进行了测试,则可以发现全局问题,重命名拼写错误等。 所有这些错误。 无论如何,您都应该进行这些测试,也许有时调试起来会有些困难,有时却不是-取决于语言和错误类型。 但是问题在于没有静态分析工具可以避免测试。 另一方面,测试……好吧,它们永远不会证明没有错误,但是经过所有测试,我感到更加安全。

-我们有一个关于测试Lua模块的问题。 作为开发人员,我想测试一些以后可以使用的局部功能。 问题是:我们希望覆盖率达到99%,但是对于此模块生成的API,它应该生成的功能案例的数量远低于其内部支持的功能。

-为什么,对不起?

-公共接口无法实现某些功能。

-如果存在公共接口无法实现的功能,则不应删除它,只需将其删除即可。 删除该代码。

-杀死它?

-是的,有时我会在Lua中这样做。 有一些代码覆盖,我无法到达那里或那里,所以我认为这是不可能的,只是删除了代码。 这并不常见,但发生了不止一次。 这些情况是不可能发生的,您只需声明一个理由就不能发生。 如果无法从公共API进入函数,则不应存在。 我们应该使用错误的输入来编码公共API,这对于测试至关重要。

-删除代码,删除效果很好,它降低了复杂性。 降低的复杂性提高了可维护性和稳定性。 保持简单。

-是的,极限编程有这个规则。 如果它不在测试中,那么它就不存在。

-创建Lua时,什么语言启发了您? 您喜欢这些语言的哪些范例或功能专业或部分内容?

-我为Lua设计了一个非常特定的目的,这不是一个学术项目。 这就是为什么当您问我是否要再次创建它时,我说这种语言有很多历史性的东西。 我不是从“让我创建我想要或想要使用的或每个人都需要的语言等开始的。 我的问题是“这里的程序需要用于地质学家和工程师的配置语言,而且我需要创建一些可以通过简单界面使用的小语言。 这就是API始终是语言不可分割的一部分的原因,因为它更易于集成。 那是目标。 在我的背景中,当时有很多不同的语言,大约有十种。 如果您想要所有背景...

-我对您想包含在Lua中的语言感兴趣。

-无论我遇到什么问题,我都从许多不同的语言那里获取信息。 唯一的最大启发是用于语法的Modula语言,但是由于语言太多,很难说。 一些东西来自AWK,这是另一个小的灵感。 当然,Scheme和Lisp ...自从我开始编程以来,我一直对Lisp着迷。

-而且在Lua中仍然没有宏!

-是的,语法有很大不同。 我认为,Fortran是第一语言...不,我学习的第一语言是汇编语言,然后是Fortran。 我学习了,但是从未使用过CLU。 我使用SNOBOL的Smalltalk进行了大量编程。 我也研究过,但从未使用过Icon,这也非常有趣。 Pascal和C带来了很多东西。当我创建Lua时,C ++对我来说已经太复杂了-那早于模板等。 那是1991年,1993年Lua开始了。

-苏联陷落,您开始创建Lua。 :)当您开始在Lua上工作时,您是否对分号和对象感到无聊? 我希望Lua具有与C类似的语法,因为它已集成到C。但是...

-是的,我认为没有相似的语法是一个很好的理由-因此,请不要混用,这是两种不同的语言。

这确实很有趣,它与您(在会议上)不允许我给出从1开始的数组的答案有关。我的答案太长了。

当我们开始Lua时,世界就不同了,并不是一切都像C。 Java和JavaScript不存在,Python尚处于起步阶段,版本低于1.0。 因此,当所有语言都应该都是C语言时,就没有这件事了。 C只是周围许多语法中的一种。

并且数组完全相同。 有趣的是,大多数人没有意识到这一点。 从零开始的数组以及从一开始的数组都有很多好处。

事实上,由于C,当今大多数流行语言都是从零开始的。它们是C的启发。有趣的是,C没有索引。 因此,您不能说C从零开始索引数组,因为没有索引操作。 C具有指针算法,因此C中的零不是索引,而是偏移量。 作为偏移量,它必须为零-并不是因为它具有更好的数学特性,或者因为它更自然(无论如何)。

并且所有复制C的语言都具有索引,并且没有指针运算。 Java,JavaScript等,等等。 -它们都没有指针算法。 所以他们只是复制了零,但这是一个完全不同的操作。 他们根本没有理由放零-就像是一个狂热的货。

-如果您要在C语言中嵌入某种语言以使其具有类似C的语法,这是合乎逻辑的。 但是,如果您使用的是C嵌入式语言,那么我假设您有C程序员,他们希望代码使用C而不是其他语言(看起来像C,但不是C)。因此,Lua用户从不应该使用C每天? 怎么了

-谁每天都会使用C?

-系统程序员。

没错 这就是问题所在,太多的人使用C,但不应允许使用它。 程序员应该被证明可以使用C。为什么软件这么坏? 所有入侵世界的黑客,所有这些安全问题。 至少有一半是由于C造成的。用C编程确实很困难。

-但Lua在C中。

-是的,这就是我们了解了用C编程的难度。您有缓冲区溢出,有整数溢出导致缓冲区溢出...只要获得一个C程序,您就可以确定如果有人把C程序弄错了,任何地方的任何数字,所有内容都会被检查。 再说一遍,真正的可移植性问题-有时有时在一个CPU上可以工作,但后来又转移到另一个CPU上。

例如,最近我们遇到了一个问题。 您如何知道您的C程序不会发生堆栈溢出? 我的意思是堆栈深度,而不是堆栈堆栈溢出,因为您已入侵...您有权在C程序中进行多少次调用?

-取决于堆栈大小。

没错 标准怎么说? 如果您使用C编写代码,然后执行此函数,该函数调用此函数,则该函数调用此函数...您可以执行多少次调用?

-一万六千?

-我可能是错的,但是我认为标准对此没有任何说明。

-我认为标准中没有任何内容,因为它过于依赖大小。

-当然,这取决于每个功能的大小。 函数框架中可能有巨大的自动数组。因此,该标准什么也没说,也没有办法检查调用是否有效。 因此,如果您有三个步骤调用,则可能会遇到一个问题,它可能崩溃并仍然是有效的C程序。 根据标准进行更正-尽管由于崩溃会导致不正确,但仍不正确。 因此,使用C进行编程非常困难,因为有太多代码。另一个很好的例子:减去两个指针会得到什么结果? 这里没有人可以和C合作吗?

-不,所以不要烤。 但是C ++支持不同的类型。

-不,C ++有同样的问题。

-声明的类型是什么? ptrdiff_t

-确实, ptrdiff_t是带符号的类型。 因此,通常,如果您有一个标准的内存,即字的大小,并且在该空间中减去了两个指针,则无法以带符号的类型表示所有大小。 那么,标准对此有何表述?

当您减去两个指针时,如果答案适合于指针差异,则为答案。 否则,您将具有未定义的行为。 您怎么知道是否合适? 你不知道 因此,每当减去两个指针时,通常就知道这是不合标准的,如果您指向大于至少2个字节的任何东西,那么较大的大小将是内存大小的一半,因此一切正常。

因此,仅在指向字节或字符时才有问题。 但是当您这样做时,您会遇到一个真正的问题,如果您不担心字符串长度大于内存的一半,就无法进行指针算术运算。 然后我不能只计算大小并存储在指针diff类型中,因为这是错误的。

我的意思是拥有真正安全的安全C或C ++程序。

-您是否考虑过使用其他语言实施Lua? 将其从C更改为其他内容?

-刚开始时,我考虑使用C ++,但是正如我所说,由于复杂性,我放弃了使用它-我无法学习全部语言。 拥有C ++的一些东西应该很有用,但是...即使到今天,我也看不到任何能用的语言。

-你能解释为什么吗?

-因为我没有其他选择。 我只能解释为什么反对其他语言。 我并不是说C是完美的,甚至不是很好,但这是最好的。 为了解释原因,我需要将其与其他语言进行比较。

-JVM呢?

-哦,JVM。 来吧,它不适合一半的硬件。可移植性是主要原因,但性能也是。 在JVM中,它比.NET更好,但是没有什么不同。 Lua所做的很多事情我们都无法通过JVM完成。 例如,您无法控制垃圾收集器。 您必须使用JVM垃圾收集器,因为您无法在JVM之上实现其他垃圾收集器。 JVM还是内存的巨大消耗者。 当任何Java程序开始打声招呼时,大约10 MB左右。 可移植性不是一个问题,不是因为它没有被移植,而是因为它不能被移植。

-像移动JVM这样的JVM修改如何?

-不是JVM,这是个玩笑。 它就像是Java的微型版本,而不是Java。

-其他静态语言(如Go或Oberon)如何? 如果您今天创建了Lua,它们可以成为Lua的基础吗?

-Oberon ...可能要视情况而定...再来,有一个垃圾回收器,并且对于Lua来说运行时太大。 Oberon是一个选择,但是Oberon有一些非常奇怪的东西,例如,如果我没记错的话,您几乎没有常数。 是的,我认为他们已将const从Pascal移至Oberon。 我有一本关于Oberon的书,并且喜欢Oberon。 它的系统令人难以置信,这确实是一件事情。

我记得在1994年,我看到了Oberon和Self的表演。 你了解自己吗? 这是与jit编译器等一起使用的一种非常有趣的动态语言。我隔一周看了这些演示,Self非常聪明,他们使用了卡通技术来掩盖操作的缓慢性。 因为当您打开某件东西时,它就像是“哇!” -首先减少一点,然后扩大一些效果。 实施得很好,他们用来模拟运动的这些技术...

然后,一周后,我们看到了Oberon的演示,该演示在Self硬件上的运行速度约为1/10的水平-有一台非常古老的小型计算机。 在Oberon中,单击然后再进行繁荣,一切立即生效,整个系统非常轻便。

但是对我来说,它太简单了,他们删除了常量和变量类型。

哈斯克尔?

-我不了解Haskell或如何在Haskell中实现Lua。

-您对Python,R或Julia这样的语言作为将来实现Lua的基础持什么态度?

-我认为其中每一个都有其用途。

R似乎对统计很有用。 它是特定领域的,由该地区的人员完成,因此这是一种优势。

Python很不错,但是我遇到了个人问题。 我以为我在谈话或访谈中提到了它。 关于不了解整个语言或不使用它的事情,即子集谬误。

我们在课程中使用Python,教授基本编程-仅一小部分,包括循环和整数。 每个人都很高兴,然后他们说拥有一些图形应用程序会很好,因此我们需要一些图形库。 几乎所有图形库都可以使用API​​ ...但是我对Python的了解还不够,这是非常先进的东西。 它有一个简单的幻觉,我拥有所有所有这些库,但它要么很简单,要么就拥有一切。

因此,当您开始使用该语言时,便会开始:哦,我必须学习OOP,继承以及其他内容。 每个图书馆。 看来作者为在其API中使用更高级的语言功能而感到自豪,以表明我不知道是什么。 函数调用,标准类型等 您有这个对象,然后如果您想要其他东西,则必须创建另一个对象...

即使是模式匹配,您也可以做一些简单的事情,但是通常标准模式匹配不是您要做的。 您进行匹配,对象返回结果,然后在该对象结果上调用方法以获取匹配的真实结果。 有时,有一种更简单的使用方法,但并不明显,这不是大多数人使用的方法。

另一个例子:我正在教一门模式匹配的课程,并且想使用类似Perl的语法,由于语法完全不同,所以我无法使用Lua。 所以我认为Python将是一个完美的例子。 但是在Python中,有一些针对某些基本内容的直接函数,但是对于更复杂的任何事情,您都必须了解对象和方法等。 我只是想做点事情,并取得结果。

-最终使用了什么?

-我使用Python并向他们解释。 但是,即使Perl更加简单,您也可以进行匹配,结果是$ 1,$ 2,$ 3,它要容易得多,但是我没有勇气使用Perl,所以...

-在发现有装饰器之前,我使用Python已有两年。 (Tarantool团队的Yaroslav Dynnikov的问题)

-是的,当您想使用库时,您必须学习这些内容,并且不了解API等。 Python给人一种幻觉,它很简单,但是很复杂。

...而且朱莉娅(Julia),我对朱莉娅(Julia)不太了解,但是从某种意义上来说,它使我想起了LuaJIT,有时看起来就像用户的骄傲。 您可以获得非常好的结果,但是您必须真正了解正在发生的事情。 这不像您编写代码并获得良好的结果。 不,您编写代码,有时效果不错,有时效果很糟。 当结果令人震惊时,您将有很多不错的工具向您展示曾经生成的中间语言,您对其进行了检查,然后遍历了几乎所有的汇编代码。 然后您意识到:哦,它并没有因此而优化。 那是程序员的问题,他们喜欢游戏,有时他们喜欢东西,因为这很困难,而不是因为容易。

我对朱莉娅(Julia)不太了解,但是我曾经看到过有关它的话题。 那个家伙在说,他就是有这种观点的人:看看它有多棒,我们编写了这个程序,它是完美的。 我不太记得,我猜是关于矩阵乘法的。 然后花车是完美的,然后双打是完美的,然后他们放置复杂的[数字] ...这是一个悲剧。 像慢一百倍。

(讽刺地)“看看它有多棒,我们有了这个工具,我们可以看到整个程序集(列表),然后您就可以改变那个那个那个了。 看看这有多有效”。 是的,我知道,我可以直接在汇编中编程。

但这只是一个话题。 我学习了一点R,并对一些小东西有使用Python的用户经验。

-您如何看待Erlang?

-Erlang是一种有趣的语言。 它有一些很好的用途,容错真的很有趣。 但是他们声称这是一种功能语言,而功能语言的整个思想就是您没有状态。

而且,Erlang在已发送和尚未接收的消息中具有巨大的隐藏状态。 因此,每个小进程都可以完全正常运行,但是程序本身却完全不正常运行。

这是一堆乱七八糟的隐藏数据,比全局变量差很多,因为如果是全局变量,则将其打印出来。 消息是系统的真实状态。 每时每刻,系统的状态是什么? 所有这些消息在这里和那里发送。 完全不起作用。

-因此,Erlang在于发挥功能,而Python则在于简单。 Lua说谎了什么?

-Lua有点小。 它仍然比大多数其他语言要小,但是如果您想使用一种非常小的语言,那么Lua就会比您想要的要大。

-那是一种小语言?

-Forth,我爱Forth。

-是否可以容纳较小版本的Lua?

-也许,但是很难。 我喜欢桌子,但是桌子不是很小。 如果您想代表小东西,桌子后面的整个想法将不适合您。 这将是Lua的语法,我们将其称为Lua,但不是Lua。

就像Java微型版一样。 您将其称为Java,但它具有多线程功能吗? 不,不是。 有反射吗? 不,不是。 那么为什么要使用它呢? 它具有Java的语法,相同的类型系统,但根本不是Java。 如果您知道Java,但不是Java,这是另一种语言,更容易学习。

如果您想制作一种看起来像Lua的小语言,但是不带表的Lua则不是。。。可能您必须声明表,例如FFI之类的就可以变小。

-Lua是否有较小的改编版?

-也许我不知道。

-Lua准备好进行纯函数式编程了吗? 你可以用Lua吗?

-当然可以。 它并不是特别有效,但只有Haskell确实有效。 如果您开始使用monad之类的东西,创建新函数,编写函数等……您可以使用Lua做到这一点,它运行起来相当合理,但是您需要不同于常规命令性语言的实现技术才能真正有效地完成工作。

— Actually, there is a library for functional programming in Lua.

— Yes, it's reasonable and usable, if you do really need performance; you can do a lot of stuff with it. I love functional stuff and I do it all the time.

— My question is more about the garbage collector, because we only have only mutable objects and we have to use them efficiently. Will Lua be good for that?

— I think a new incarnation of garbage collector will help a lot, but again…

— Young die young? The one that seems to work with young objects?

— Exactly, yes. But as I said even with the standard garbage collector we don't have optimal performance but it can be reasonable. More often you don't even need that performance for most actions unless you are writing servers and having big operations.

— What functional programming tasks do you perform in Lua?

— A simple example. My book, I'm writing my own format and I have a formatter that transforms that in LaTex or DocBook. It's completely functional, it has a big pattern matching… It's slightly inspired by LaTex but much more uniformed. There's @ symbol instead of backslash, a name of a macro and one single argument in curly brackets. So I have gsub that recognizes this kind of stuff and then it calls a function, the function does something and returns something. It's all functional, just functions on top of functions on top of functions, and the final function gives a big result.

— Why don't you program with LaTeX?

— Plain LaTeX? First, it's too tricky for a lot of stuff and so difficult. I have several things that I don't know how to do in LaTex. For example, I want to put a piece of inline code inside a text. Then there is a slash verb, standard stuff. But slash verb gives fixed space. And the space between stuff is never right. All real spaces are variable, it depends on how the line is adjusted, so it expands in some spaces and compacts in others depending on a lot of stuff. And those spaces are fixed, so sometimes they look too large, sometimes too small. It also depends on what you put in code.

— But you still render your own format to LaTeX?

— Yes, but with a lot of preprocessing. I write my own verb but then it changes and becomes not a verb but a lot of stuff. For example, when I write 3+1 I write a very small space here. In verb, if I don't put any space here, it shrinks, and if I do, it's too large. So I do the preprocessing, inserting a variable space. It's very small but can be a little larger if it needs to adjust. But if I put 'and' after 1 then I put a larger space. This function here does all that. This is a small example but there are other things…

— Do you have a source?

— I do have the source, it is in the git . The program's called 2html . The current version only generates HTML… Sorry, that's a kind of a mess. I created it for a book but also another one for the manual. The one in the git is for the manual. But the other one is more complicated and not public, I can't make it public. But the main problem is that TeX is not there. It's almost impossible to process TeX files without TeX itself.

— Is it not machine-readable?

— Yes, it's not machine-readable. I mean, it is readable because TeX reads it. It's so hard to test, so many strange rules etc. So this is much more uniformed and as I said I generate DocBook format, sometimes I need it. That started when I had this contract for a book.

— So you use 2html to generate DocBook?

— Yes, it generates DocBook directly.

— Ok, thank you very much for the interview!



If you have any more questions, you can ask them in the Lua Mailing List . See you soon!

Source: https://habr.com/ru/post/zh-CN459466/


All Articles