美文网首页
位运算的几种应用

位运算的几种应用

作者: leejnull | 来源:发表于2020-01-08 22:31 被阅读0次

例1:不借助临时变量,交换两个数的值

思路:通过异或,先求出两个变量的不同的位

var a = 10
var b = 8

a = a ^ b
b = a ^ b
a = a ^ b

例2:求一个UInt二进制数中1的个数

思路:比如一个 1011 0100 这个二进制数,先用 1(0000 0001)和它做"与"操作,如果结果为 1,说明在最右边的这一位是 1,继续把 1 左移 1 位重复比较

func getCountOfOne(num: UInt) -> UInt {
    var count: UInt = 0
    var temp = num
    var loopCount = 0
    while temp != 0 {
        count += (temp & 1)
        temp = (temp >> 1)
        loopCount += 1
    }
    print("loop1 count: \(loopCount)")
    return count
}

上述算法有一个可以优化的地方,当有这样一个数 1100 0000,如果还是从最右边往左判断的话,有大量的 0 是没有必要的,我们可以从左边开始,让 num 和 num-1 这两个数做"与"运算,如果结果为 0,则说明这个数后续已经没有 1 了,反之继续比较

func getCountOfOne2(num: UInt) -> UInt {
    var count: UInt = 0
    var temp = num
    var loopCount = 0
    while temp != 0 {
        count += 1
        temp = temp & (temp-1)
        loopCount += 1
    }
    print("loop2 count: \(loopCount)")
    return count
}

例3:判断一个UInt数是否为2的整数幂次方

思路:能成为 2 的整数次幂的数,其二进制一定是这种类型的:1000 0000,如果 1000 0000 和它的 -1 后的数 0111 1111 做"与"操作,结果就是 0

func isPowerOfTwo(num: UInt) -> Bool {
    return (num & (num-1)) == 0
}

例4:找丢失数

一堆成对出现的数:1,2,3,4,3,2,1,找出其中缺失的一个数

思路:给定一个初始值,和数组里面的所有数做"异或"操作,成对出现的数和0做完异或操作后,结果依然是0,最后缺失的那个数4和0做异或操作,结果依然是4

func findLostNum(nums: [UInt]) -> UInt {
    var lostNum: UInt = 0
    for num in nums {
        lostNum = lostNum ^ num
    }
    return lostNum
}

如果有两个数缺失呢?

思路:分两组来计算。先求他们的异或结果,然后找出可以区分缺失的两个数的最右边为1的位的flag(缺失的两个数最右侧为1的位数肯定是不一样的),遍历数组,根据num和flag的"与"运算是否为0,分为2组,分别做异或运算,这里就和上面的过程一致了。

func findTwoLostNums(nums: [UInt]) -> (UInt, UInt) {
    var num1: UInt = 0
    var num2: UInt = 0
    var temp: UInt = 0
    for num in nums {
        // 得到缺失的两个数的结果
        temp = temp ^ num
    }
    // 找到最后为1的位
    var flag: UInt = 1
    while (flag & temp) == 0 {
        flag = flag << 1
    }
    // 找两个丢失的数字
    for num in nums {
        if (flag & num) == 0 {
            num1 = num1 ^ num
        } else {
            num2 = num2 ^ num
        }
    }
    return (num1, num2)
}

来自 https://leejnull.github.io/2019/09/07/2019-09-07/

相关文章

  • 位运算的几种应用

    例1:不借助临时变量,交换两个数的值 思路:通过异或,先求出两个变量的不同的位 例2:求一个UInt二进制数中1的...

  • 位运算应用

    取模 由于偶数的最低位为 0,奇数为 1,所以取模运算可以用位操作来代替。 取整 位掩码 通过定义这些选项,可以用...

  • 位运算的应用

    位运算 程序中的所有数在计算机内存中都是以二进制的形式存储的。位运算说穿了,就是直接对整数在内存中的二进制位进行操...

  • 位运算及其应用

    内容概要: 位运算基本操作 基于位运算的状态压缩 位运算经典应用 位运算解N皇后问题 位运算 符号描述规则&与1&...

  • 位运算符

    位运算符就是用来操作二进制的位的,java提供了几种操作位的运算。位运算只能用于整型类型,char或者double...

  • 位运算与应用

    转载自http://blog.csdn.net/u012713968/article/details/504816...

  • Java位运算的应用

    一、判断整数的奇偶性 传统思路: 按照传统的思路,判断一个整数的奇偶性是通过用这个数与2求模,看运算结果是否为0 ...

  • C语言的位操作(Two)

    一、位运算赋值运算符 闲话就不多说,直接上图咯。 位运算赋值运算符 二、位运算应用 **eg:取一个整数a从右端开...

  • python3从零学习-4.3、运算符

    运算符用于执行程序代码运算 python运算符有以下几种: 算术运算符 比较运算符 赋值运算符 位运算符 逻辑运算...

  • Scala编程基础7:Scala运算符

    Scala含有丰富的内置运算符,包括以下几种类型: 算术运算符 关系运算符 逻辑运算符 位运算符 赋值运算符 接下...

网友评论

      本文标题:位运算的几种应用

      本文链接:https://www.haomeiwen.com/subject/tyreactx.html