Sök…


Anmärkningar

Booléer, sanning och falska är okomplicerade i Lua. Att recensera:

  1. Det finns en boolesisk typ med exakt två värden: true och false .
  2. I ett villkorat sammanhang ( if , elseif , while , until ), krävs ingen boolean. Vilket uttryck som helst kan användas.
  3. I villkorat sammanhang räknas false och nil som falskt, och allt annat räknas som sant.
  4. Även om 3 redan antyder detta: om du kommer från andra språk, kom ihåg att 0 och den tomma strängen räknas som sant i villkorade sammanhang i Lua.

Den booleska typen

Booléer och andra värden

När du arbetar med lua är det viktigt att skilja mellan de booleska värdena true och false och värden som utvärderas till sant eller falskt.

Det finns bara två värden i lua som utvärderar till falskt: nil och false , medan allt annat, inklusive siffran 0 utvärderar till sant.

Några exempel på vad detta betyder:

if 0 then print("0 is true") end --> this will print "true"
if (2 == 3) then print("true") else print("false") end --> this prints "false"
if (2 == 3) == false then print("true") end --> this prints "true"
if (2 == 3) == nil then else print("false") end
--> prints false, because even if nil and false both evaluate to false,
--> they are still different things.

Logiska operationer

Logiska operatörer i lua returnerar inte nödvändigtvis booleska värden:

and kommer att returnera det andra värdet om det första värdet utvärderas till sant;

or returnerar det andra värdet om det första värdet utvärderas till falsk;

Detta gör det möjligt att simulera den ternära operatören, precis som på andra språk:

local var = false and 20 or 30 --> returns 30
local var = true and 20 or 30 --> returns 20
-- in C: false ? 20 : 30

Detta kan också användas för att initialisera tabeller om de inte finns

tab = tab or {} -- if tab already exists, nothing happens

eller för att undvika att använda if-uttalanden, vilket gör koden lättare att läsa

print(debug and "there has been an error") -- prints "false" line if debug is false
debug and print("there has been an error") -- does nothing if debug is false
-- as you can see, the second way is preferable, because it does not output
-- anything if the condition is not met, but it is still possible.
-- also, note that the second expression returns false if debug is false,
-- and whatever print() returns if debug is true (in this case, print returns nil)

Kontrollera om variabler är definierade

Man kan också enkelt kontrollera om en variabel finns (om den är definierad), eftersom icke-existerande variabler returnerar nil , vilket utvärderas till falskt.

local tab_1, tab_2 = {}
if tab_1 then print("table 1 exists") end --> prints "table 1 exists"
if tab_2 then print("table 2 exists") end --> prints nothing

Det enda fallet där detta inte gäller är när en variabel lagrar värdet false , i vilket fall det finns tekniskt men fortfarande utvärderar till falskt. På grund av detta är det en dålig design att skapa funktioner som returnerar false och nil beroende på tillstånd eller ingång. Vi kan dock fortfarande kontrollera om vi har nil eller false :

if nil == nil then print("A nil is present") else print("A nil is not present") end
if false == nil then print("A nil is present") else print("A nil is not present") end
-- The output of these calls are:
-- A nil is present!
-- A nil is not present

Villkorade sammanhang

Villkorliga sammanhang i Lua ( if , elseif , while , until ) kräver inte booleska. Liksom många språk kan alla Lua-värden visas i ett skick. Reglerna för utvärdering är enkla:

  1. false och nil räknas som falskt.

  2. Allt annat räknas som sant.

    if 1 then
      print("Numbers work.")
    end
    if 0 then
      print("Even 0 is true")
    end
    
    if "strings work" then
      print("Strings work.")
    end
    if "" then
      print("Even the empty string is true.")
    end
    

Logiska operatörer

I Lua kan booleaner manipuleras genom logiska operatörer . Dessa operatörer inkluderar not , and , och or .

I enkla uttryck är resultaten ganska enkla:

print(not true) --> false
print(not false) --> true
print(true or false) --> true
print(false and true) --> false

Rangordning

Företrädesordning liknar matematikoperatörerna unary - , * och + :

  • not
  • sedan and
  • or

Detta kan leda till komplexa uttryck:

print(true and false or not false and not true)
print( (true and false) or ((not false) and (not true)) )
    --> these are equivalent, and both evaluate to false

Genväg utvärdering

Operatörerna and och or kanske bara utvärderas med den första operand, förutsatt att den andra är onödig:

function a()
    print("a() was called")
    return true
end

function b()
    print("b() was called")
    return false
end

print(a() or b())
    --> a() was called
    --> true
    --  nothing else
print(b() and a())
    --> b() was called
    --> false
    --  nothing else
print(a() and b())
    --> a() was called
    --> b() was called
    --> false

Idiomatisk villkorad operatör

På grund av de logiska operatörernas företräde, möjligheten till genvägsutvärdering och utvärdering av icke- false och icke- nil som true , finns en idiomatisk villkorad operatör tillgänglig i Lua:

function a()
    print("a() was called")
    return false
end
function b()
    print("b() was called")
    return true
end
function c()
    print("c() was called")
    return 7
end

print(a() and b() or c())
    --> a() was called
    --> c() was called
    --> 7
    
print(b() and c() or a())
    --> b() was called
    --> c() was called
    --> 7

På grund av karaktären av x and a or b struktur a aldrig kommer att returneras om det beräknas till false , kommer detta villkorade då alltid tillbaka b oavsett vad x är.

print(true and false or 1)  -- outputs 1

Sanningstabeller

Logiska operatörer i Lua "returnerar" inte booleska, utan ett av deras argument. Använd nil för falskt och siffror för sant, här är hur de beter sig.

print(nil and nil)       -- nil
print(nil and 2)         -- nil
print(1 and nil)         -- nil
print(1 and 2)           -- 2

print(nil or nil)        -- nil
print(nil or 2)          -- 2
print(1 or nil)          -- 1
print(1 or 2)            -- 1

Som ni ser kommer Lua alltid att returnera det första värdet som gör att kontrollen misslyckas eller lyckas . Här är sanningstabellerna som visar det.

  x  |  y  || and            x  |  y  || or
------------------         ------------------
false|false||  x           false|false||  y   
false|true ||  x           false|true ||  y   
true |false||  y           true |false||  x   
true |true ||  y           true |true ||  x

För dem som behöver det, här är två funktioner som representerar dessa logiska operatörer.

function exampleAnd(value1, value2)
  if value1 then
    return value2
  end
  return value1
end

function exampleOr(value1, value2)
  if value1 then
    return value1
  end
  return value2
end

Emulera Ternary Operator med 'och' 'eller' logiska operatörer.

I lua returnerar de logiska operatörerna and och or en av operandema som resultat istället för ett booleskt resultat. Som en konsekvens kan denna mekanism utnyttjas för att emulera den ternära operatörens beteende trots att lua inte har en "verklig" ternär operatör på språket.

Syntax

villkor och sanningen_expr eller falsey_expr

Använd i variabel tilldelning / initialisering

local drink = (fruit == "apple") and "apple juice" or "water"

Använd i bordskonstruktör

local menu =
{
  meal  = vegan and "carrot" or "steak",
  drink = vegan and "tea"    or "chicken soup"
}

Använd som funktionsargument

print(age > 18 and "beer" or "fruit punch")

Använd i uttalande

function get_gradestring(student)
  return student.grade > 60 and "pass" or "fail"
end

Varning

Det finns situationer där denna mekanism inte har önskat beteende. Överväg detta fall

local var = true and false or "should not happen"

I en "verklig" ternär operatör är det förväntade värdet på var false . I lua faller emellertid and utvärderingen "igenom" eftersom den andra operanden är falsey. Som ett resultat var slutar med should not happen stället.

Två möjliga lösningar på detta problem, refaktor detta uttryck så att den mellersta operand inte är falsey. t.ex.

local var = not true and "should not happen" or false

eller alternativt använda den klassiska if then else konstruera.



Modified text is an extract of the original Stack Overflow Documentation
Licensierat under CC BY-SA 3.0
Inte anslutet till Stack Overflow