首页 > 其他分享 >位运算骚操作

位运算骚操作

时间:2024-05-08 13:34:12浏览次数:20  
标签:return 运算 int 异或 ans 操作 uint32

位运算骚操作

异或操作

异或运算性质

1)异或运算就是无进位相加
2)异或运算满足交换律、结合律,也就是同一批数字,不管异或顺序是什么,最终的结果都是一个
3)0^n=n,n^n=0
4)整体异或和如果是x,整体中某个部分的异或和如果是y,那么剩下部分的异或和是x^y

骚操作

  • 交换两个数
void exchange(int &a, int &b)
{
    if(a == b) return; //防止&a,&b指向同一个地址;那样结果会错误。
    a ^= b ^= a ^= b;
}
  • 不用任何判断语句和比较操作,返回两个数的最大值
// 非负数返回1 负数返回0
int sign(int n)
{
	return !(unsigned int)n >> 31;
}

void  getmax(int a, int b)
{
    // c可能溢出
    int c = a - b;
    // a的符号
    int sa = sign(a);
    // b的符号
    int sb = sign(b);
    // c的符号
    int sc = sign(c);
    // 判断A和B,符号是不是不一样,不一样就返回1, 一样就返回0
    int diffAB = sa ^ sb;
    // 判断A和B,符号是不是一样,一样就返回1, 不一样就返回0
    int sameAB = !diffAB;
    
    int returnA = diffAB * sa + sameAB * sc;
    int returnB = !returnA;
    return a * returnA + b * returnB
}
  • 找到缺失的数字

https://leetcode.cn/problems/missing-number/

class Solution {
public:
    int missingNumber(vector<int>& nums) {
        int all = 0, miss = 0;
        int size = nums.size();
        for(int i = 0; i < size; i ++ )
        {
            all ^= i;
            miss ^= nums[i];
        }
        all ^= size;
        return all ^ miss;
    }
};
  • 提取出二进制里最右侧的1
// Brian Kernighan算法
int right_one(int x)
{
    return x & (-x);  // 返回int,但是32位里只有1个位置是1,且为最右边那个
}

位运算的骚操作

  • 判断一个整数是不是2的幂
// Brian Kernighan算法
bool isPowerOfTwo(int n)
{
    return n > 0 && n == (n & -n);
}
  • 判断一个数是不是3的幂
// 如果一个数字是3的某次幂,那么这个数一定只含有3这个质数因子
// 1162261467是int型范围内,最大的3的幂,它是3的19次方
// 这个1162261467只含有3这个质数因子,如果n也是只含有3这个质数因子,那么
// 1162261467 % n == 0
// 反之如果1162261467 % n != 0 说明n一定含有其他因子
bool isPowerOfThree(int n)
{
    return n > 0 && (1162261467 % n == 0);
}

bool isPowerOfThree2(int n)
{
    while(n && (n % 3 == 0)) n /= 3;
    return n == 1;
}

  • 抹去最右边的1
n = n & (n - 1);
  • 逆序二进制的状态

https://leetcode.cn/problems/reverse-bits/

// 位运算分治
class Solution {
private:
    const uint32_t M1 = 0x55555555; // 01010101010101010101010101010101
    const uint32_t M2 = 0x33333333; // 00110011001100110011001100110011
    const uint32_t M4 = 0x0f0f0f0f; // 00001111000011110000111100001111
    const uint32_t M8 = 0x00ff00ff; // 00000000111111110000000011111111

public:
    uint32_t reverseBits(uint32_t n) {
        n = n >> 1 & M1 | (n & M1) << 1;
        n = n >> 2 & M2 | (n & M2) << 2;
        n = n >> 4 & M4 | (n & M4) << 4;
        n = n >> 8 & M8 | (n & M8) << 8;
        return n >> 16 | n << 16;
    }
};

位运算实现加减乘除

int add(int a, int b)
{
    int sumtmp = a ^ b;
    int carry = (a & b) << 1;
    while(carry)
    {
		int temp = sumtmp;
        sumtmp = temp ^ carry;
        carry = (tmep & carry) << 1;
    }
    return sumtmp;
}

int neg(int n) // 取反
{
    return add(~n, 1);
}

int minus(int a, int b)  // a - b
{
    return add(a, neg(b));
}

int multiply(int a, int b)
{
    int ans = 0;
    unsigned int c = (unsigned int)b;
    while(b != 0)
    {
		if((b & 1) != 0)
        {
			ans = add(ans, a);
        }
        a <<= 1;
        c >>= 1;
    }
    return ans;
}

int div(int a, int b)
{
    int x = a < 0 ? meg(a) : a;
    int y = b < 0 ? neg(b) : b;
    int ans = 0;
    for(int i = 30; i >= 0; i = minus(i, 1))
    {
        if((x >> i) >= y)
        {
			ans |= (1 << i);
            x = minus(x, y << i);
        }
    }
    return ((a < 0) ^ (b < 0)) ? neg(ans) : ans;
}

标签:return,运算,int,异或,ans,操作,uint32
From: https://www.cnblogs.com/hnu-hua/p/18179471

相关文章

  • excel 汇总运算后生成柱状图
    defsum(df,q_name,sum_index):#df=pd.DataFrame#pd_frame.sum()#print(df.values)#Aggregations(聚合),多索引,,'季度'df_agg=df.groupby(['厂家','季度'])['销量'].agg([np.sum])......
  • selenium操作浏览器的一些配置
    selenium操作浏览器的一些配置#设置用户代理USER_AGENTS=['Mozilla/5.0(WindowsNT10.0;Win64;x64)AppleWebKit/537.36(KHTML,likeGecko)Chrome/58.0.3029.110Safari/537.3','Mozilla/5.0(WindowsNT6.1;WOW64)AppleWebKit/537.36(KHTML,......
  • 《最新出炉》系列入门篇-Python+Playwright自动化测试-44-鼠标操作-上篇
    1.简介前边文章中已经讲解过鼠标的拖拽操作,今天宏哥在这里对其的其他操作进行一个详细地介绍和讲解,然后对其中的一些比较常见的、重要的操作单独拿出来进行详细的介绍和讲解。2.鼠标操作语法鼠标操作介绍官方API的文档地址:https://playwright.dev/docs/api/class-mouseMouse鼠......
  • Linux基础04-Linux中目录和文件都能操作的命令
    前面两节我们分别学习了目录操作命令和文件操作命令,那么有没有一些既可以操作目录,又可以操作文件的命令呢?这样我们就不需要记住两套命令了。其实还真有,今天这一章就带大家学习Linux中目录和文件都能操作的命令最近无意间获得一份阿里大佬写的刷题笔记,一下子打通了我的任督二脉......
  • 创建个人博客网站记录-2.3 建立模型以及对应的CRUD操作
    2.3、建立模型以及对应的CRUD操作在本节中,创建了USER用户类和BLOG博文类两个对象类,并实现了其基本的增删改查的操作。#flaskr/models.pyfromflaskimportgfromflask_sqlalchemyimportSQLAlchemyfromsqlalchemyimportColumn,Integer,String,TIMESTAMP,ForeignKey,T......
  • 操作系统
    操作系统是控制和管理计算机硬件和软件资源、合理地组织计算机工作流程以及方便用户有效地使用计算机的程序集合。操作系统的四个基本特征(1)并发性--宏观并行,微观串行。在多道程序环境下,并发性是指两个或多个事件在同一时间间隔内发生,即宏观上有多道程序同时执行,而微观上,在单处理机......
  • Linux基础03-Linux文件操作命令
    其实啊,说起计算机操作,大部分情况下就是“增删改查”这四个大字儿,文件操作也是这么回事儿。就是改文件的时候得用点专门的编辑器,比如那个Vim。不过Vim这东西,真心不是一两句话就能给你讲清楚的,咱们在后续的章节再好好说道说道。现在学文件操作命令的时候,如果得改文件内容,咱们就先......
  • QRCoderHelper-二维码的操作工具类
    /***┌──────────────────────────────────────────────────────────────┐*│描述:二维码QRCoder的操作工具类(QRCoder1.5.1)*│作者:执笔小白*│版本:1.0*│创建时间:2023-06-2216:21:56*......
  • 2024ICPC武汉邀请赛-G.Pack-数论分块、整除运算相关的不等式
    link:https://codeforces.com/gym/105143Groupcontests:https://codeforces.com/group/DWEH34LQgT/contest/521901题意:有\(n\)件\(A\)物品,\(m\)件\(B\)物品,两种物品价值分别是\(a,b\),若干件\(A\)和若干件\(B\)可以打包成一个商品,打包尽可能多的商品的情况下让剩余的......
  • Linux与Windows操作系统的爱恨情仇(初料)
    Linux与Windows操作系统的爱恨情仇(初料)更改时间:四种常见文件系统比较(FAT16、FAT32、NTFS、ExFAT)MMU内存管理单元Linux系统内核的作用Linux系统目录和Windows系统文件夹的区别1.四种常见文件系统比较(FAT16、FAT32、NTFS、ExFAT)FAT16、FAT32、NTFS和ExFAT是四......