数组中只出现一次的数字(一个整型数组里除了两个数字之外,其他的数字都出现了两次。请写程序找出这两个只出现一次的数字):
解法在于位运算中的异或,直接异或可以得到这两个数的异或,按照最后的有效数字位可以分为两个数组,然后分别异或得到各自的值;
void FindNumsAppearOnce(vector<int> data,int* num1,int *num2) { if(data.size()==0) return; *num1=0; *num2=0; vector<int> data1,data2; int res=0,flag=0; for(auto &i : data) res^=i; while(!(res&1)){ res>>=1; flag++; } int num=1<<flag; for(auto &i : data){ if(i&num) data1.push_back(i); else data2.push_back(i); } for(int &i : data1) *num1^=i; for(int &i : data2) *num2^=i; return; }
二进制中1的个数:
int NumberOf1(int n) { int count=0; while(n){ count++; n=n&(n-1); //把最后的1给消除掉,总共消除了几次,就证明有几个1 } return count; }
数字在排序数组中出现的次数
class Solution { public: int res=0; //全局变量 int GetNumberOfK(vector<int> data ,int k) { int size=data.size(); if(size<=0) return 0; getn(data,0,size-1,k); return res; } int getn(vector<int> &data,int start, int end, int k){ if(start>end) return 0; //退出条件 int mid=(start+end)/2; //二分 复杂度logn if(data[mid]==k){ res++; //更改出现次数 getn(data,start,mid-1,k); getn(data,mid+1,end,k); } else if(data[mid]<k){ getn(data,mid+1,end,k); } else getn(data,start,mid-1,k); return 0; } };
//可以改为当找到匹配点,从左右开始找相同的,然后直接退出递归
if(k[mid]==a){ res++; int i=mid; while((--i)>=0&&k[i]==a){ res++; } while((++mid)<10&&k[mid]==a){ res++; } return 0; }
数据流中的中位数:采用两个堆,O(N)的复杂度
class Solution { public: void Insert(int num) { ++count; if(count&1){ //如果是奇数个数的元素,则先放入小顶堆,然后把小顶堆中的顶放到大顶堆中 min_heap.push(num); max_heap.push(min_heap.top()); min_heap.pop(); } else{ max_heap.push(num); min_heap.push(max_heap.top()); max_heap.pop(); } } double GetMedian() { if(count&1) return max_heap.top(); else return (max_heap.top()+min_heap.top())/2.0; } private: int count=0; priority_queue<int, vector<int>, less<int>> max_heap; priority_queue<int, vector<int>, greater<int>> min_heap; };