百度360必应搜狗淘宝本站头条
当前位置:网站首页 > IT知识 > 正文

Lua 中的三目运算符介绍(三目运算符的语法)

liuian 2025-03-20 16:22 11 浏览

Lua 原生的语义并没有实现三目运算,一般是通过逻辑运算符 and 和 or 来模拟三目运算符的。

三目运算

熟悉 C/C++ 的老司机都知道三目运算 a ? b : c,这种写法替换简单的条件判断语句可以在不增加阅读难度的情况下,使代码尽量保持简洁。

int a, b, ret;
//if-else
if (a > b)
    ret = a;
else
    ret = b;

//三目运算符
ret = a > b ? a : b;

Lua 中的三目运算

Lua 原生的语义并没有实现三目运算,一般是通过逻辑运算符 and 和 or 来模拟三目运算符的。

Lua 中 and 和 or 都使用"短路求值(short_cur evaluation)",也就是说,它们只会在需要时才去评估第二个操作数。(《Lua程序设计》)

local a, b, ret;
ret = a > b and a or b

穷举所有可能性:

a > b 时:

a > b and a –> true 
a or b –> a

a <= b时:

a > b and a –> false 
a or b –> b

完美!

Lua 中的三目运算符陷阱

按照从特殊到一般的原则:

  • 三目运算的一般形式a ? b : ca = true,结果为b
    a = false,结果为c
  • 对应Lua中的a and b or cb = truea = truea and b –> trueb or c –> ba = falsea and b –> falseb or c –> cb = falsea = truea and b –> falseb or c –> ca = falsea and b –> falseb or c –> c

可以看到当 b = false 时,Lua模拟的 a and b or c 始终返回 c 并不能还原三目运算符的原貌。

《Lua程序设计》也建议这种情况使用 if-else 来避免。

一般化的 a and b or c

那么有没有办法可以解决 b = false 失效的问题呢?

由此我联想到 C 语言有一道常规的考题:请使用宏定义写一个返回两个值中较小值的方法。

在校时第一次看到本题,第一反应如下:

#define MIN(A,B) A < B ? A : B

然而这种写法在很多嵌套的使用环境中都不能返回正确的结果。比如:2 * MIN(3, 4)展开为 2 * 3 < 4 ? 3 : 4 = 6 < 4 ? 3 : 4,结果为4。 更"工程师"的写法是:

#define MIN(A,B) ((A) < (B) ? (A) : (B))

还有好奇心的同学可以参考:宏定义的正确写法,三目运算的宏定义

从这个示例中,我就在想如何能保证 a and b or c 中 b 为真或者 b 不产生歧义呢?

  1. and的运算优先级高于or,简单的改变运算顺序并没有用。
  2. 这时就想到了lua中万能的table,能不能把a,b,c都放到table中来改变b的存在呢?要注意{nil}也是一个为true的对象。
    a,b,c都替换为table:{a} and {b} or {c}。
  3. 三目运算中a是条件,结果是b或者c。其实a并不需要放入table中,否则{a}就始终为true了,失去了条件的意义。而{b} or
    {c}的结果也必然是一个table,该table只有一个元素。那么通过[1]即可访问。
  4. 综上所述,更一般化的Lua三目运算为:(a and {b} or {c})[1]

总结

诚然,要想知道Lua中三目运算的形式,只需通过搜索就可以找到想要的答案。上述的推理过程多少有点先知道答案,故意往答案上靠的嫌疑。不过我坚信证明一个问题,结论并不是最重要的,重要的是论证的过程。本文仅以我对Lua粗浅的认知来尝试还原一般化的Lua三目运算的推导过程,如有更好的推理过程,可以一起交流。

Lua 中的三目运算符介绍 | 《Linux就该这么学》 (linuxprobe.com)

相关推荐

C# - StreamWriter与StreamReader 读写文件 101

读写文本文件的方式:1)File静态类的File.ReadAllLines();与File.WriteAllLines();方法进行读写2)FileStream实例类的对象fs.Read();与fs....

第5天:文件操作——与真实世界连接

程序,不只是屏幕上跑,真正有用的程序,能处理文件。今天学习最基础的文件读写:#写入文件withopen('hello.txt','w',encoding=&#...

C语言数据输出和输入介绍

在C语言中,数据的输出和输入是程序与用户或外部环境进行交互的重要方式之一。通过数据的输出,程序可以向用户展示信息或结果;通过数据的输入,程序可以获取用户提供的数据或参数。本文将深入介绍C语言中数据输出...

Python 中Print() 函数的秘密!你知道吗

print()函数通常是初学者遇到的第一个Python函数。它是一个基本工具,是进入编程世界的初始门户。它允许开发人员在程序执行期间展示信息、变量和消息。然而,尽管print()函数无处不...

解决U盘exe病毒,exe病毒查杀

U盘exe病毒难以清除,即使被杀毒软件删除也会复活,相当顽固。我曾深受其害,经过多次尝试,终于找到解决办法。若此方法对您有用,请记得点个赞支持。1、U盘中毒后,根目录下的文件夹会变成隐藏状态,无法直...

利用python数据分析,获取双色球历史中奖信息!(内含详细代码)

前言:毫无例外,基本上是所有人都有一颗中奖的心,不管是有钱的,还是没钱的!你们说对吗?对于技术人员来说,通过技术分析,可以增加中奖几率,现使用python语言收集历史双色球中奖信息,之后进行预测分析。...

C语言实战之文件复制

在C语言中,复制文件可以通过读取源文件的内容并将其写入目标文件来实现。以下是一个简单的示例程序,演示如何复制文件。示例代码#include<stdio.h>#include<s...

用Python一分钟搞定了本要一晚才能做完的800张奖状海报

随着互联网公司的兴起,编程技术越来越吃香,尤其是Python。其实不用说,你也应该发现了,现在稍微有些粉丝的公众号,都接有Python的广告。这说明了什么?说明真的火!但是我今天不是来推Python的...

手把手教你玩转Copy命令

一.简介COPY命令是Windows操作系统中一个广泛使用的命令行工具,它用于复制文件和目录。与在资源管理器中进行操作不同,COPY命令可以通过指定源文件和目标位置来进行复制,使得它可以自动...

学习VB编程第20天,文件读取写入

今天学习了刘金玉老师VB编程教程的第28期,学习的主要内容是文件读取写入。1.dountil......loop循环语句①语法结构dountil条件表达式的值类型符合条件的要执行的代码.........

新手学Python避坑,学习效率狂飙! 二十一、print()函数

感谢大家对《新手学Python避坑,学习效率狂飙!》系列的点赞、关注和收藏,今天这编是这个系列的第二十一个分享,前面还有二十个,大家可以关注下之前发布的文章。下面是我们今天第三个的分享:在Pytho...

如何用python的requests来下载网页内容保存到txt

如何用python的requests来下载网页内容保存到txtimportrequests#定义目标网页和保存路径url="http://www.5a8.com"fil...

Windows下如何将WSL安装到非C盘?三种实用方法分享!

Windows下如何将WSL安装到非C盘?三种实用方法分享!前言随着微软对Linux支持的不断加强,WSL(WindowsSubsystemforLinux)已成为众多开发者的得力工具。然而,很...

C#程序注册成服务

某些时候我们需要一个程序在电脑开机后就自动启动,无界面运行在后台。比如数据上传功能,我们需要在电脑开机后程序就自动启动,上传我们需要的数据,而不是每次开机都要手动去运行程序。1、新建一个项目,该项目实...

怎么在Python中读取和写入文件?

Python是一种高级编程语言,它提供了许多内置函数和模块,可用于读取和写入文件。读取和写入文件是Python编程中非常基本和必要的操作,因为很多应用程序需要从外部文件中读取数据,或将数据写入外部文件...