136.Single number [LeetCode]

熟练使用map


136_Single_number    

Given an array of integers, every element appears twice except for one. Find that single one.

Note:Your algorithm should have a linear runtime complexity. Could you implement it without using extra memory?

只有一个光棍,其余元素均成对出现,找出这个苦逼的光棍!再见

/*
   ^ 异或运算,不同为1,相同为0;
   1^1=0;
   0^0=0;
   1^0=1;
   0^1=1;
   先转换成二进制,然后异或,3^5 → 11^101=110  → 6.   

   还有一个用途,交换两个数的值:
   a=a^b;
   b=a^b;  // b=a^b^b=a,  b^b 抵消所以a^b^b得a,实现b=a,把a赋值给b
   a=a^b;  // 带入最原始的a,b值 ☞ a=(a^b)^(a^b)^b,抵消之后剩余b
*/

class Solution {
public:
	int singleNumber(vector<int>& nums) 
	{
		int result = 0;
		for (int i = 0; i!= nums.size(); ++i)
		{
			result ^= nums[i];
		}
		return result;
	}
};


其它解法:

class Solution
{
public:
	int singleNumber(vector<int> &nums){
		unordered_map<int, int> cnts;    // {number, count}
		for (auto x : nums){
			if (cnts.find(x) != cnts.end())
			    cnts[x]++;
			else
			    cnts.insert({ x, 1 });
		}

		for (auto x : cnts){
		   if (x.second != 2)
			return x.first;
		}
		return 0;
	}
};
class Solution
{
public:
	int singleNumber(vector<int> &nums)
	{
		int n = 0;
		for (auto x : nums)
		{
			n ^= x;
		}
		return n;
	}
};
class Solution {
public:
	int singleNumber(vector<int>& nums) {
		sort(nums.begin(), nums.end());
		for (int i = 0; i<nums.size(); i += 2)
			if (nums[i] != nums[i + 1])
				return nums[i];
		return 0;
	}
};


137_Single_Number II

Given a non-empty array of integers, every element appears three times except for one, which appears exactly once. Find that single one.

继续找出这个万众瞩目的光棍!

扫描二维码关注公众号,回复: 1050356 查看本文章
class Solution{
public:
	int singleNumber(std::vector<int> &nums){
		std::unordered_map<int, int> cnts;    // {number, count}
		for (auto x : nums){
			if (cnts.find(x) != cnts.end())
			    cnts[x]++;			
			else
			    cnts.insert({ x, 1 });
		}

		for (auto x : cnts){
		    if (x.second != 3)			
			return x.first;			
		}
		return 0;
	}
};

其他方法:
class Solution {
public:
	int singleNumber(vector<int>& nums) 
	{
		int one = 0, two = 0, three = 0;
		for (auto i : nums) 
		{
			two |= (one & i);
			one ^= i;
			three = ~(one & two);
			one &= three;
			two &= three;
		}
		return one;
	}
};
class Solution {
public:
	int singleNumber(vector<int>& nums) {
		int a = 0, b = 0;
		for (int i = 0; i < nums.size(); ++i) {
			b = (b ^ nums[i]) & ~a;
			a = (a ^ nums[i]) & ~b;
		}
		return b;
	}
};
class Solution {
public:
	int singleNumber(vector<int>& nums) {
		const int W = sizeof(int) * 8;
		int count[W];
		std::fill_n(&count[0],W, 0);
		for (int i = 0; i < nums.size(); i++) {
			for (int j = 0; j < W; j++) {
				count[j] += (nums[i] >> j) & 1;
				count[j] %= 3;
			}
		}
		int result = 0;
		for (int i = 0; i < W; i++) {
			result += (count[i] << i);
		}
		return result;
	}
};

260_Single_Number_III

Given an array of numbers nums, in which exactly two elements appear only once and all the other elements appear exactly twice. Find the two elements that appear only once.

这次厉害了,有两个光棍,其余元素均成对存在。把这俩光棍挑出来!得意

用最笨的方法,万能的map,但是效率可能不是很理想

class Solution {
public:
    vector<int> singleNumber(vector<int>& nums) {
        	
        vector<int>result;
        unordered_map<int, int> cnts;    // {number, count}  
		for (auto x : nums){
			if (cnts.find(x) != cnts.end())
				cnts[x]++;
			else
				cnts.insert({ x, 1 });
		}

		for (auto x : cnts)
		{
			if (x.second == 1)
				result.push_back(x.first);
		}
		return result;
    }
};
136、137、260都是相似问题,都能用暴力的map解决,哈哈,map真是个好东西啊.

575_Distribute_Candies

    Given an integer array with even length, where different numbers in this array represent different kinds of candies. Each number means one candy of the corresponding kind. You need to distribute these candies equally in number to brother and sister. Return the maximum number of kinds of candies the sister could gain.

Example 1:

Input: candies = [1,1,2,2,3,3]
Output: 3
Explanation:
There are three different kinds of candies (1, 2 and 3), and two candies for each kind.
Optimal distribution: The sister has candies [1,2,3] and the brother has candies [1,2,3], too. 
The sister has three different kinds of candies. 

Example 2:

Input: candies = [1,1,2,3]
Output: 2
Explanation: For example, the sister has candies [2,3] and the brother has candies [1,1]. 
The sister has two different kinds of candies, the brother has only one kind of candies.


class Solution 
{
public:
	int distributeCandies(vector<int>& candies) {
		if (candies.size() % 2 != 0)
			return 0;
		unordered_map<int, int> HASH;
		int res = 0;
		for (int c : candies) {
			HASH[c]++;
			if (HASH[c] == 1 && res<candies.size() / 2)
				res++;
		}
		return res;
	}
}
//其他方法
	int distributeCandies1(vector<int>& candies) 
	{
		assert(candies.size() % 2 == 0);//assert宏的原型定义在<assert.h>中,其作用是如果它的条件返回错误,则终止程序执行
		sort(begin(candies), end(candies));//将数组排序
		int ans = 1;//记录糖果种类
		for (int i = 0; i!=candies.size()-1; ++i) {
			if (/*i == 0 ||*/ candies[i] != candies[i + 1])
				++ans;
		}
		return min(ans, (int)candies.size() / 2);
	}


//其他方法
	int distributeCandies2(vector<int>& candies) 
	{return min(unordered_set<int>(candies.cbegin(), candies.cend()).size(), candies.size() / 2);}

1_Two_Sum

    Given an array of integers, return indices of the two numbers such that they add up to a specific target.

You may assume that each input would have exactly one solution, and you may not use the same element twice.

Example:

Given nums = [2, 7, 11, 15], target = 9,

Because nums[0] + nums[1] = 2 + 7 = 9,
return [0, 1].

#include<unordered_map>
using std::vector;
using std::unordered_map;
class Solution {
public:
	vector<int> twoSum(vector<int>& nums, int target) {
		unordered_map<int, int> _map;
		vector<int>result;
		for (int i = 0; i != nums.size(); ++i)
		{
			_map[nums[i]] = i;
		}
		for (auto i = 0; i != nums.size(); ++i)
		{
			const int gap = target - nums[i];
			if (_map.find(gap)!= _map.end() && _map[gap] > i)
			{
				result.push_back(i );
				result.push_back(_map[gap] );
			}
		}
		return result;
	}
};









猜你喜欢

转载自blog.csdn.net/mc_007/article/details/78487441