原题网址:http://www.lintcode.com/zh-cn/problem/single-number-ii/
给出3*n + 1 个的数字,除其中一个数字之外其他每个数字均出现三次,找到这个数字。
样例
给出 [1,1,2,3,3,3,2,2,4,1] ,返回 4
标签
非挑战版AC代码:
思路依旧是先排序,再遍历。每隔两个数(每三个数)做一次减法,若差值不为零返回被减数,一直遍历到第n-1个数,若一直无输出,说明最后一个元素是落单的数,将该值return出去。
1 class Solution {
2 public:
3 /**
4 * @param A: An integer array
5 * @return: An integer
6 */
7 int singleNumberII(vector<int> &A) {
8 // write your code here
9 if (A.empty())
10 {
11 return NULL;
12 }
13 int size=A.size();
14 sort(A.begin(),A.end());
15 for (int i=0;i<size-1;i+=3)
16 {
17 if (A[i]-A[i+1]!=0)
18 {
19 return A[i];
20 }
21 }
22 return A[size-1];
23 }
24 };
挑战:一次遍历,常数级的额外空间复杂度
参考: https://blog.csdn.net/wangyuquanliuli/article/details/46637377
https://blog.csdn.net/zaqwsx20/article/details/52823538?utm_source=itdadao&utm_medium=referral
C++中位运算的使用方法
位操作,统计所有数字各个位上数字的和,除以3取余就是落单数在这个位上的值。
1 class Solution {
2 public:
3 /**
4 * @param A: An integer array
5 * @return: An integer
6 */
7 int singleNumberII(vector<int> &A) {
8 // write your code here
9 int buf[32]={0}; //int类型32个位;
10 for (int i=0;i<(int)A.size();i++) //计算数组中所有元素各个位的和(二进制),存放在数组buf中;
11 {
12 addBuf(A[i],buf);
13 }
14 int result=0;
15 for (int j=0;j<32;j++)
16 {
17 int val=buf[j]%3; //各个位的和对3取余数,val值非0即1;
18 result=(val<<j|result); //由数组恢复成整数(注意是二进制运算),j是第几位,所以需要左移j;
19 } //或运算保证之前的结果不丢失;
20 return result;
21 }
22
23 void addBuf(int x,int *buf)
24 {
25 for (int i=0;i<32;i++)
26 {
27 buf[i]=buf[i]+(x>>i&1);
28 }
29 }
30 };