如何在Lua中使用按位异或运算符XOR?

20
我该如何在Lua语言中实现位运算符?具体来说,我需要一个异或运算符/方法。
7个回答

33
在 Lua 5.2 中,你可以使用 bit32 库中的函数。
在 Lua 5.3 中,bit32 库已经被弃用,因为现在有原生的位运算符
print(3 & 5)  -- bitwise and
print(3 | 5)  -- bitwise or
print(3 ~ 5)  -- bitwise xor
print(7 >> 1) -- bitwise right shift
print(7 << 1) -- bitwise left shift
print(~7)     -- bitwise not

输出:

1
7
6
3
14
-8

11

在Lua 5.2中,您可以使用bit32.bxor函数。


10

由于您参考了3次取整函数,对于大多数操作使用了过多的循环(小于2 ^ 31的数字不需要所有31个循环),使用了^运算符,并且没有充分利用a和b可能是具有不同数量级的不同数字的事实,您会损失很多效率。该功能也没有本地化,您还要进行两个不必要的除法运算。我编写这个函数是为了尽可能快。

一般来说,您将看到约3到20倍的改进。

local function BitXOR(a,b)--Bitwise xor
    local p,c=1,0
    while a>0 and b>0 do
        local ra,rb=a%2,b%2
        if ra~=rb then c=c+p end
        a,b,p=(a-ra)/2,(b-rb)/2,p*2
    end
    if a<b then a=b end
    while a>0 do
        local ra=a%2
        if ra>0 then c=c+p end
        a,p=(a-ra)/2,p*2
    end
    return c
end

如果你需要更多的功能,比如AND、OR和NOT,那么我也能够提供。

local function BitOR(a,b)--Bitwise or
    local p,c=1,0
    while a+b>0 do
        local ra,rb=a%2,b%2
        if ra+rb>0 then c=c+p end
        a,b,p=(a-ra)/2,(b-rb)/2,p*2
    end
    return c
end

local function BitNOT(n)
    local p,c=1,0
    while n>0 do
        local r=n%2
        if r<1 then c=c+p end
        n,p=(n-r)/2,p*2
    end
    return c
end

local function BitAND(a,b)--Bitwise and
    local p,c=1,0
    while a>0 and b>0 do
        local ra,rb=a%2,b%2
        if ra+rb>1 then c=c+p end
        a,b,p=(a-ra)/2,(b-rb)/2,p*2
    end
    return c
end

别担心,你不需要改变任何东西。


5

如果你需要一种高效的位移方式,我曾经写过一篇关于这个的文章。下面是一些使用该技术的函数:

function lshift(x, by)
  return x * 2 ^ by
end

function rshift(x, by)
  return math.floor(x / 2 ^ by)
end

1
新地址 https://ebens.me/post/simulate-bitwise-shift-operators-in-lua/ - Баян Купи-ка

1

尝试:

function xor(a,b)
 return (a or b) and not (a and b)
end 

0

来自楼主的内容;从问题移动到此回答中。


这是我在Lua中实现XOR的方法:

local floor = math.floor
function bxor (a,b)
  local r = 0
  for i = 0, 31 do
    local x = a / 2 + b / 2
    if x ~= floor (x) then
      r = r + 2^i
    end
    a = floor (a / 2)
    b = floor (b / 2)
  end
  return r
end

-2



这很简单。使用NAND逻辑。 https://en.wikipedia.org/wiki/NAND_logic

function xor(a,b)
    return not( not( a and not( a and b ) ) and not( b and not( a and b ) ) )
end

如果您也需要 1、0 输入,请将以下内容插入函数中。
    a = a==1 or a == true   -- to accept nil, 1, 0, true or false
    b = b==1 or b == true   -- to accept nil, 1, 0, true or false

希望这能帮助到某个人。

op 询问的是按位异或,而不是布尔异或 此外,您可以使用不等运算符 a ~= b 具有与 "a xor b" 完全相同的含义 - joe pelletier
2
降低投票,因为它不必要地复杂化了a ~= b,已经完成了布尔异或的工作。 - Fox

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