题目:一个整型数组里除了两个数字之外,其他的数字都出现了两次。请写程序找出这两个只出现一次的数字。要求时间复杂度是O(n),空间复杂度是O(1)。
思路:题目要求时间复杂度是O(n),空间复杂度是O(1),这说明基于比较的办法求解无法完成,这题需要异或的性质,异或(同为0,异为1,相当于不进位加法)
因为其它数都出现两次,当扫描完一次之后,将所有的数做异或,那些相同的数都会变成0,结果是两个不同的数的异或。例如,9,4,4,2做异或,4,4异或为0,结果就相当于9异或2。
这里有两个数字不同,假设只有一个数字不同,那么,我们只需要扫描一遍,所有数做异或就可以得出结果。有两个数字怎么办呢?思路就是将这两个数划分到两个不同的组去。
划分依据是什么呢?
1,可以这么做,先将所有的数异或起来,假设结果为11001100,那么可以用最低的1位划分(即第2位,低到高,从0数起)[实质上可以用任何一个1划分,只是这是最方便的],为什么1可以划分开两个不同的数呢?将两个数写成二进制的形式,那么异或结果显示出的1位(同时两个不同的数相异或必然有1,因为同则必为0),都是二者相应位不同的。(异为1,同为0),因此用1划分则不同的两数必然被分到两个不同组
2,第二步,将两个子数组的数做异或就能得出结果,因为相同的数会得0.
3,小技巧,中途需要判断位是否为1,方法是:先将要判断的位通过右移移到最末位,然后与0000.....00001