LeetCode Python 位操作 1
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了LeetCode Python 位操作 1相关的知识,希望对你有一定的参考价值。
Python 位操作:
按位与 &, 按位或 |
体会不到
按位异或 ^
num ^ num = 0
左移 <<
num << 1 == num * 2**1
右移 >>
num >> 2 == num / 2**2
取反 ~
~num == -(num + 1)
1. 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?
关键点在于相同整数按位异或为0, 整数与0异或不变, 一个 reduce 搞定. LeetCode 执行效率击败 18.9%.
class Solution(object): def singleNumber(self, nums): """ :type nums: List[int] :rtype: int """ return reduce(lambda x,y: x^y, nums)
2. Single Number II
Given an array of integers, every element appears three times except for one, which appears exactly once. Find that single one.
Note:
Your algorithm should have a linear runtime complexity. Could you implement it without using extra memory?
下三路的解法, 如果看到这个答案, 就应该问一下 sum 和 set 的时间空间复杂度各是多少, 为什么. LeetCode: 72.45%.
class Solution(object): def singleNumber(self, nums): """ :type nums: List[int] :rtype: int """ return (sum(set(nums)) * 3 - sum(nums)) / 2
3. Reverse bits of a given 32 bits unsigned integer.
For example, given input 43261596 (represented in binary as 00000010100101000001111010011100), return 964176192 (represented in binary as 00111001011110000010100101000000).
Follow up:
If this function is called many times, how would you optimize it?
首先, Python 没有原生对于 unsigned integer 的支持, 其次, 这个是同样下三路的解法. LeetCode: 85.2%.
class Solution: # @param n, an integer # @return an integer def reverseBits(self, n): string = bin(n) if n >= 0: string = string[:2] + string[2:].zfill(32)[::-1] else: string = string[:3] + string[3:].zfill(32)[::-1] return int(string, 2)
4. Number of 1 Bits
Write a function that takes an unsigned integer and returns the number of ’1‘ bits it has (also known as the Hamming weight).
For example, the 32-bit integer ’11‘ has binary representation 00000000000000000000000000001011
, so the function should return 3.
这样刷题一点意思都没有, count 的时间空间复杂度是多少. LeetCode: 62.81%.
class Solution(object): def hammingWeight(self, n): """ :type n: int :rtype: int """ string = bin(n) return string.count("1")
5. Bitwise AND of Numbers Range
Given a range [m, n] where 0 <= m <= n <= 2147483647, return the bitwise AND of all numbers in this range, inclusive.
For example, given the range [5, 7], you should return 4.
如果用 range, 会报内存不足, 用 xrange 会报超时. 我自己把 [0, 2147483647] 带入, 确实跑不动.
class Solution(object): def rangeBitwiseAnd(self, m, n): """ :type m: int :type n: int :rtype: int """ return reduce(lambda x,y: x&y, xrange(m, n+1))
观察一下, 其实它的关键是, log(n, 2) 比 log(m, 2) 大多少, 如果大于 1, 那么肯定就是0, 如果小于 1, 就再进行 reduce. LeetCode: 2.52%.
class Solution(object): def rangeBitwiseAnd(self, m, n): """ :type m: int :type n: int :rtype: int """ if m == 0: return 0 from math import log logm = log(m, 2) logn = log(n, 2) if logn - logm >= 1: return 0 return reduce(lambda x,y: x&y, xrange(m, n+1))
而使用 log 是明显的作弊, 再顺着刚才的思路, 之前都是从 m 开始考虑, 现在从 n 开始考虑, 因为 & 操作会使 n 迅速下降, 两种情况, 一种是遍历 [m, n] 的 &, 另一种半路上就有0出来了. 并且, 我相信耗时的大户应该是 xrange, 位操作本身应该很快. LeetCode: 70.18%.
class Solution(object): def rangeBitwiseAnd(self, m, n): """ :type m: int :type n: int :rtype: int """ while m < n: n &= n - 1 return n
增加 if n == 0 判断, 如果是 0 就 break, 看看能提升多少. LeetCode: 73.09%.
class Solution(object): def rangeBitwiseAnd(self, m, n): """ :type m: int :type n: int :rtype: int """ while m < n: n &= n - 1 if n == 0: break return n
6. Power of Two
Given an integer, write a function to determine if it is a power of two.
首先, 2的0次方为 1, 因此 n >= 1, 然后, 就是对 n 执行 >>= i, 如果 n 是 2 的幂, 那么 n >> i << i == n, 注意我们的目标是计算 i 让 n >> i == 2, 所以 i - 1. LeetCode: 45.27%.
class Solution(object): def isPowerOfTwo(self, n): """ :type n: int :rtype: bool """ if n < 1: return False i, m = 0, n while m: m >>= 1 i += 1 return n >> (i - 1) << (i - 1) == n
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.
For example:
Given nums = [1, 2, 1, 3, 2, 5]
, return [3, 5]
.
Note:
- The order of the result is not important. So in the above example,
[5, 3]
is also correct. - Your algorithm should run in linear runtime complexity. Could you implement it using only constant space complexity?
首先是下三路的解法, 必然会超时
class Solution(object): def singleNumber(self, nums): """ :type nums: List[int] :rtype: List[int] """ results = [] for i in set(nums): if nums.count(i) == 1: results.append(i) if len(results) == 2: return results
应该还是在考察位操作, 相同的数变成 0 而不同相同的数留下来. 如果全局异或, 最终的值是两个数字的异或. 这个涉及到位操作的细节, 凑不出来了.
我不准备用位操作解这个问题, collections 这个神库里面有个 Counter 类, 参数是 iterable 的对象, 对对象中的 hashable 对象进行计数.
sorted 可以对字典的 values 进行排序. LeetCode: 45.7%.
class Solution(object): def singleNumber(self, nums): """ :type nums: List[int] :rtype: List[int] """ from collections import Counter counter = Counter(nums) return [_[0] for _ in sorted(counter.items(), key=lambda x: x[1])[:2]]
268. Missing Number
Given an array containing n distinct numbers taken from 0, 1, 2, ..., n
, find the one that is missing from the array.
For example,
Given nums = [0, 1, 3]
return 2
.
Note:
Your algorithm should run in linear runtime complexity. Could you implement it using only constant extra space complexity?
等差数列之和, LeetCode: 78.18%.
class Solution(object): def missingNumber(self, nums): """ :type nums: List[int] :rtype: int """ length = len(nums) gauss_sum = length * (length - 1) / 2 + length nums_sum = sum(nums) return gauss_sum - nums_sum
318. Maximum Product of Word Lengths
Given a string array words
, find the maximum value of length(word[i]) * length(word[j])
where the two words do not share common letters. You may assume that each word will contain only lower case letters. If no such two words exist, return 0.
Example 1:
Given ["abcw", "baz", "foo", "bar", "xtfn", "abcdef"]
Return 16
The two words can be "abcw", "xtfn"
.
Example 2:
Given ["a", "ab", "abc", "d", "cd", "bcd", "abcd"]
Return 4
The two words can be "ab", "cd"
.
Example 3:
Given ["a", "aa", "aaa", "aaaa"]
Return 0
No such pair of words.
相当然的解法是遍历列表配合 set, 结果必然超时了.
class Solution(object): def maxProduct(self, words): """ :type words: List[str] :rtype: int """ results = [0] length = len(words) for i in xrange(length): item_i = words[i] for item_j in words[i:]: if len(set(item_i + item_j)) == len(set(item_i)) + len(set(item_j)): results.append(len(item_i) * len(item_j)) return max(results)
两个 for, 复杂度是 O(n**2), 不用跑都知道会超时. 如果能降到 O(nlogn) 说不定还有戏. 那能知道什么时候该停下么? 不知道, 先过.
342. Power of Four
Given an integer (signed 32 bits), write a function to check whether it is a power of 4.
Example:
Given num = 16, return true. Given num = 5, return false.
Follow up: Could you solve it without loops/recursion?
tmp > 1 也就是最小值 >>= 到 4的0次幂, 也就是 1, 然后再还原回来. LeetCode: 70.80%
class Solution(object): def isPowerOfFour(self, num): """ :type num: int :rtype: bool """ if num < 1: return False i, tmp = 0, num while tmp > 1: tmp >>= 2 i += 2 return num >> i << i == num
371. Sum of Two Integers
Calculate the sum of two integers a and b, but you are not allowed to use the operator +
and -
.
Example:
Given a = 1 and b = 2, return 3.
完全没想法, 过.
389. Find the Difference
Given two strings s and t which consist of only lowercase letters.
String t is generated by random shuffling string s and then add one more letter at a random position.
Find the letter that was added in t.
Example:
Input: s = "abcd" t = "abcde" Output: e Explanation: ‘e‘ is the letter that was added.
没想法.
以上是关于LeetCode Python 位操作 1的主要内容,如果未能解决你的问题,请参考以下文章
位操作系列2-leetcode136(c++/python)
LeetCode 1486 数组异或操作[位运算 数学] HERODING的LeetCode之路