打印出出现奇数次的整数

1:题目

给定一个整数数组aar,其中只有两个数出现了奇数次,其他的数都出现了偶数次,找出这个数。

例如:

aar=[1,5,1,5,2,6,4,6],

返回2,4

 

2:要求

  要求时间的复杂度为O(n),额外的空间复杂度为O(1)

 

3:解答

1:首先可以知道整数k和0异或的结果为k,整数k和k异或的结果为0,这是异或的规律。

2:如果只有一个数出现奇数次,比如array=[2,3,3],那么通过异或操作,最后获取到的结果就是我们需要找的数2。

 

这是什么原因呢?可以举例说明一下,

2的二进制是0010,3的二进制是0011,那么2^3的结果是0001,再次和3异或,结果为0010,而0010的十进制是2,

异或运算符满足交换律和结合律,同时结合1所说的规律,所以任意调整数组的位置不会改变运算的结果。

对于任何的数组,只要这个数组有一个数出现了奇数次,另外的数出现了偶数次,最后异或的结果都是出现了奇数次的数。

 

代码可见下面的代码部分。

那么如果有2个数出现奇数次,我们可以用同样的方法考虑。

a:首先申请一个变量x,那么数组最后异或的结果肯定是两个出现奇数次的数的异或结果,把它赋值给x。

b:x肯定能在32的位整数中找到不等于0的bit位,假如第k位不等于0,说明这两个出现奇数次的数,一个数在第k位为0,一个在第k位为1。

c:接下来再次对这个数组分组,一个数组是第k位都是0的数的组合,另一个数组是第k位都是1的数的组合。

 

那么这个分组怎么分呢 ???思考一下......

一个数n的相反数可以直接~n+1,一个数和自己的相反数进行位与,得到的是原数中右起第一个为1,其余都为0的数。

比如5的原码 00000000 00000000 00000000 00000101

则-5在计算机中表达为:11111111 11111111 11111111 11111011

d:再分别对两个数组进行各自的异或操作,两个数组获取到的结果就是我们需要找的两个数。

 

4:代码


如果你觉得这篇文章有用,记得分享关注下面的公众号,大家一起进步哦~~~

 

扫一扫 关注我的公众号

如果你想要跟大家分享你的文章,欢迎留言投稿~

如果你喜欢,请留下你的赞哦

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值