目录
121.买卖股票的最佳时机 Best Time to Buy and Sell Stock
125.验证回文串 Valid Palindrome
136.只出现一次的数字 Single Number
167.两数之和 II - 输入有序数组 Two Sum II - Input array is sorted
168.表的名称 Excel Sheet Column Title
169.求众数 Majority Element
171.Excel Sheet Column Number
172.阶乘后的零 Factorial Trailing Zeroes
189.旋转数组 Rotate Array
190.颠倒二进制位 reverse-bits
"""
给定一个数组,它的第 i 个元素是一支给定股票第 i 天的价格。
如果你最多只允许完成一笔交易(即买入和卖出一支股票),设计一个算法来计算你所能获取的最大利润。
注意你不能在买入股票前卖出股票。
示例 1:
输入: [7,1,5,3,6,4]
输出: 5
解释: 在第 2 天(股票价格 = 1)的时候买入,在第 5 天(股票价格 = 6)的时候卖出,最大利润 = 6-1 = 5 。
注意利润不能是 7-1 = 6, 因为卖出价格需要大于买入价格。
示例 2:
输入: [7,6,4,3,1]
输出: 0
解释: 在这种情况下, 没有交易完成, 所以最大利润为 0。
"""
# 超过时间限制
'''
def maxProfit(prices):
n = len(prices)
m = 0
for i in range(n):
for j in range(i, n):
if prices[j] > prices[i]:
temp = prices[j] - prices[i]
if temp > m:
m = temp
return m
'''
'''
def maxProfit(prices):
n = len(prices)
m = 0
for i in range(n-1):
t = max(prices[i+1:])
if prices[i] < t:
temp = t - prices[i]
if temp > m:
m = temp
return m
'''
def maxProfit1(prices):
if not prices:
return 0
ans = 0
pre = prices[0]
for i in range(1, len(prices)):
pre = min(pre, prices[i])
ans = max(prices[i] - pre, ans)
return ans
def maxProfit2(prices):
min = 2 ** 31
max = 0
for x in prices:
if x < min:
min = x
elif x - min > max:
max = x - min
return max
a = [7, 1, 5, 3, 6, 4]
c = maxProfit1(a)
print(c)
"""
给定一个字符串,验证它是否是回文串,只考虑字母和数字字符,可以忽略字母的大小写。
说明:本题中,我们将空字符串定义为有效的回文串。
示例 1:
输入: "A man, a plan, a canal: Panama"
输出: true
示例 2:
输入: "race a car"
输出: false
"""
def isPalindrome1(s):
start, end = 0, len(s) - 1
while start < end:
if not s[start].isalnum():
start += 1
continue
if not s[end].isalnum():
end -= 1
continue
if s[start].lower() != s[end].lower():
return False
start += 1
end -= 1
return True
def isPalindrome2(s):
# 提取所有字母和数字
s = [c for c in s if c .isalpha() or c.isdigit()]
if len(s) <= 1:
return True
i, j = 0, len(s) - 1
while i < j:
if s[i].lower() != s[j].lower():
return False
i, j = i + 1, j - 1
return True
def isPalindrome3(s):
# filter(判断函数,可迭代对象),str.isalnum():检测字符串是否由字符串和数字组成,也不能有空格
if s is None:
return True
s = ''.join(filter(str.isalnum, s)).lower()
return s == s[::-1]
a = "A man, a plan, a canal: Panama"
c = isPalindrome2(a)
print(c)
'''
给定一个非空整数数组,除了某个元素只出现一次以外,其余每个元素均出现两次。找出那个只出现了一次的元素。
说明:
你的算法应该具有线性时间复杂度。 你可以不使用额外空间来实现吗?
示例 1:
输入: [2,2,1]
输出: 1
示例 2:
输入: [4,1,2,1,2]
输出: 4
'''
def singleNumber1(nums):
for i in range(len(nums)-1):
if nums[i] in nums[:i] or nums[i] in nums[i+1:]:
pass
else:
return nums[i]
def singleNumber2(nums):
return sorted(nums)[len(nums)//2]
a = [4, 1, 2, 1, 2]
print(singleNumber2(a))
'''
给定一个已按照升序排列 的有序数组,找到两个数使得它们相加之和等于目标数。
函数应该返回这两个下标值 index1 和 index2,其中 index1 必须小于 index2。
说明:
返回的下标值(index1 和 index2)不是从零开始的。
你可以假设每个输入只对应唯一的答案,而且你不可以重复使用相同的元素。
示例:
输入: numbers = [2, 7, 11, 15], target = 9
输出: [1,2]
解释: 2 与 7 之和等于目标数 9 。因此 index1 = 1, index2 = 2 。
'''
def twoSum(numbers, target):
d = {}
for i, num in enumerate(numbers):
if target - num in d:
return [d[target - num]+1, i+1]
d[num] = i
a = [2, 7, 11, 15]
c = twoSum(a, 9)
print(c)
'''
给定一个正整数,返回它在 Excel 表中相对应的列名称。
例如,
1 -> A
2 -> B
3 -> C
...
26 -> Z
27 -> AA
28 -> AB
...
示例 1:
输入: 1
输出: "A"
示例 2:
输入: 28
输出: "AB"
示例 3:
输入: 701
输出: "ZY"
'''
def convertToTitle1(n):
s = ''
while n:
n, b = n//26, n % 26
if b == 0 and n > 0:
s = 'Z' + s
n = n - 1
else:
s = chr(b+64) + s
return s
def convertToTitle2(n):
ans = ''
while n:
ans = chr((n-1) % 26+65)+ans
n = (n-(n-1) % 26-1)//26
return ans
c = convertToTitle2(52)
print(c)
"""
给定一个大小为 n 的数组,找到其中的众数。众数是指在数组中出现次数大于 ⌊ n/2 ⌋ 的元素。
你可以假设数组是非空的,并且给定的数组总是存在众数。
示例 1:
输入: [3,2,3]
输出: 3
示例 2:
输入: [2,2,1,1,1,2,2]
输出: 2
"""
def majorityElement(nums):
return sorted(nums)[len(nums)//2]
a = [2, 2, 1, 1, 1, 2, 2]
b = majorityElement(a)
print(b)
"""
给定一个Excel表格中的列名称,返回其相应的列序号。
例如,
A -> 1
B -> 2
C -> 3
...
Z -> 26
AA -> 27
AB -> 28
...
示例 1:
输入: "A"
输出: 1
示例 2:
输入: "AB"
输出: 28
示例 3:
输入: "ZY"
输出: 701
"""
def titleToNumber(s):
a = list(s)
n = 0
s = len(a)
for i in range(s):
n += (ord(a[i])-64) * 26**(s-i-1)
return n
a = "AB"
n = titleToNumber(a)
print(n)
"""
给定一个整数 n,返回 n! 结果尾数中零的数量。
示例 1:
输入: 3
输出: 0
解释: 3! = 6, 尾数中没有零。
示例 2:
输入: 5
输出: 1
解释: 5! = 120, 尾数中有 1 个零.
说明: 你算法的时间复杂度应为 O(log n) 。
"""
def trailingZeroes1(n):
a = 0
while n >= 5:
a += n//5
n = n//5
return a
def trailingZeroes2(n):
s = 5
summ = 0
while n >= s:
summ += n//s
s *= 5
return summ
a = trailingZeroes2(30)
print(a)
'''
给定一个数组,将数组中的元素向右移动 k 个位置,其中 k 是非负数。
示例 1:
输入: [1,2,3,4,5,6,7] 和 k = 3
输出: [5,6,7,1,2,3,4]
解释:
向右旋转 1 步: [7,1,2,3,4,5,6]
向右旋转 2 步: [6,7,1,2,3,4,5]
向右旋转 3 步: [5,6,7,1,2,3,4]
示例 2:
输入: [-1,-100,3,99] 和 k = 2
输出: [3,99,-1,-100]
解释:
向右旋转 1 步: [99,-1,-100,3]
向右旋转 2 步: [3,99,-1,-100]
说明:
尽可能想出更多的解决方案,至少有三种不同的方法可以解决这个问题。
要求使用空间复杂度为 O(1) 的原地算法。
'''
def rotate1(nums, k):
"""
Do not return anything, modify nums in-place instead.
"""
n = k % len(nums)
for i in range(n):
nums.insert(0, nums[-1])
nums.pop(-1)
def rotate2(nums, k):
n = len(nums)
k %= n
nums[:n] = nums[:n][::-1]
nums[:k] = nums[:k][::-1]
nums[k:n] = nums[k:n][::-1]
'''
[1, 2, 3, 4, 5, 6, 7]
[7, 6, 5, 4, 3, 2, 1]
[5, 6, 7, 4, 3, 2, 1]
[5, 6, 7, 1, 2, 3, 4]
'''
def rotate3(nums, k):
n = len(nums)
k = k % n
nums[0:n] = nums[n-k:] + nums[0:n-k]
a = [1, 2, 3, 4, 5, 6, 7]
k = 3
rotate3(a, k)
print(a)
"""
颠倒给定的 32 位无符号整数的二进制位。
示例 1:
输入: 00000010100101000001111010011100
输出: 00111001011110000010100101000000
解释: 输入的二进制串 00000010100101000001111010011100 表示无符号整数 43261596,
因此返回 964176192,其二进制表示形式为 00111001011110000010100101000000。
示例 2:
输入:11111111111111111111111111111101
输出:10111111111111111111111111111111
解释:输入的二进制串 11111111111111111111111111111101 表示无符号整数 4294967293,
因此返回 3221225471 其二进制表示形式为 10101111110010110010011101101001。
"""
def reverseBits1(n):
res = '{0:032b}'.format(n)
res = res[::-1]
return int(res, 2)
def reverseBits2(n):
ans = 0
mask = 1
for _ in range(32):
ans <<= 1
if mask & n:
ans |= 1
n >>= 1
return ans
a = 1000000
c = reverseBits1(a)
print(c)