3. 无重复字符的最长子串 力扣https://leetcode-cn.com/problems/longest-substring-without-repeating-characters/
class Solution(object):
def lengthOfLongestSubstring(self, s):
"""
:type s: str
:rtype: int
"""
last = {}
start = 0
ans = 0
for i in range(len(s)):
if s[i] in last:
start = max(start, last[s[i]] + 1)
last[s[i]] = i
ans = max(ans, i-start+1)
return ans
# Definition for singly-linked list.
# class ListNode(object):
# def __init__(self, val=0, next=None):
# self.val = val
# self.next = next
class Solution(object):
def reverseKGroup(self, head, k):
"""
:type head: ListNode
:type k: int
:rtype: ListNode
"""
length = 0
p1 = head
while p1: #计算链表长度
length += 1
p1 = p1.next
pre = None
cur = head
for _ in range(length // k): #这个循环用于计算周期
start = pre
end = cur
for _ in range(k): #这个循环用于反转k个节点
temp = cur.next
cur.next = pre
pre = cur
cur = temp
if start:
start.next = pre #连接上一个K长度子链表的尾节点和下一个K长度子链表的头节点
else:
head = pre #第一个周期要把head指向正确的链表头, pre是新链表的头结点
end.next = cur #cur指向下一个K长度子链表的头节点
pre = end #pre指向cur前一个节点(上一个K长度链表的尾节点)
return head
# Definition for singly-linked list.
# class ListNode(object):
# def __init__(self, val=0, next=None):
# self.val = val
# self.next = next
class Solution(object):
def reverseList(self, head):
"""
:type head: ListNode
:rtype: ListNode
"""
cur = head
pre = None
while cur:
temp = cur.next # 保存一下 cur的下一个节点,因为接下来要改变cur->next
cur.next = pre #反转
pre = cur #反转
cur = temp
return pre
力扣215. 数组中的第K个最大元素 (用的快排)力扣https://leetcode-cn.com/problems/kth-largest-element-in-an-array/
class Solution(object):
def findKthLargest(self, nums, k):
"""
:type nums: List[int]
:type k: int
:rtype: int
"""
def partition(arr, low, high):
i = (low - 1) # 最小元素索引
pivot = arr[high]
for j in range(low, high):
# 当前元素小于或等于 pivot
if arr[j] <= pivot:
i = i + 1
arr[i], arr[j] = arr[j], arr[i]
arr[i + 1], arr[high] = arr[high], arr[i + 1]
return (i + 1)
def quickSort(arr, low, high):
if low < high:
pi = partition(arr, low, high)
quickSort(arr, low, pi - 1)
quickSort(arr, pi + 1, high)
quickSort(nums, 0, len(nums)-1)
return nums[-k]
146. LRU 缓存机制 LeetCode-python 146.LRU缓存机制 - 简书https://www.jianshu.com/p/77d14cf02196力扣https://leetcode-cn.com/problems/lru-cache/
class LRUCache(object):
def __init__(self, capacity):
"""
:type capacity: int
"""
self.capacity = capacity
self.catch = collections.OrderedDict()
def get(self, key):
"""
:type key: int
:rtype: int
"""
if key not in self.catch: #关键字不在缓存中 返回-1
return -1
value = self.catch.pop(key) #关键字在缓存中,返回关键字的值
self.catch[key] = value
return value
def put(self, key, value):
"""
:type key: int
:type value: int
:rtype: None
"""
if key in self.catch: #如果关键字已经存在 变更数据值
self.catch.pop(key)
elif self.catch and self.capacity == 0: #缓存达到上限,删除最久未使用的数据值
self.catch.popitem(last=False) #popitem()可以的到最后一个进表的value,而popitem(last=False)可以得到第一个进表的value
else:#关键字不存在
self.capacity -= 1 #插入之后记得容量减一
self.catch[key] = value
本身题目不难但是要理解题意,注意要用有序字典,以及popitem()。用了这么久字典不知道有序字典。。。
103. 二叉树的锯齿形层序遍历 力扣https://leetcode-cn.com/problems/binary-tree-zigzag-level-order-traversal/
class Solution(object):
def zigzagLevelOrder(self, root):
"""
:type root: TreeNode
:rtype: List[List[int]]
"""
if not root:
return []
queue = [root]
res = []
flag = 1
while queue:
templist = []
length = len(queue)
for i in range(length):
temp = queue.pop(0)
templist.append(temp.val)
if temp.left:
queue.append(temp.left)
if temp.right:
queue.append(temp.right)
if flag == -1:#偶数次遍历是从右往左
templist=templist[::-1]
res.append(templist)
flag *= -1
return res
class Solution(object):
def levelOrder(self, root):
if not root:
return []
queue=[root]
res=[]
cur=[]
while queue:
curCount=len(queue)
for i in range(0,curCount): #一个curcount循环是一层的结点
root=queue.pop(0)
cur.append(root.val)
if root.left:
queue.append(root.left)
if root.right:
queue.append(root.right)
res.append(cur)
cur=[]
return res
class Solution(object):
def preorderTraversal(self, root):
"""
:type root: TreeNode
:rtype: List[int]
"""
if not root:
return []
stack = [root]
res = []
while stack:
cur = stack.pop()
res.append(cur.val)
if cur.right:
stack.append(cur.right)
if cur.left:
stack.append(cur.left)
return res
94. 二叉树的中序遍历
力扣https://leetcode-cn.com/problems/binary-tree-inorder-traversal/
class Solution(object):
def inorderTraversal(self, root):
stack, res = [], []
cur = root
while stack or cur:
if cur:
stack.append(cur)
cur = cur.left
else:
cur = stack.pop()
res.append(cur.val)
cur = cur.right
return res
class Solution(object):
def postorderTraversal(self, root):
"""
:type root: TreeNode
:rtype: List[int]
"""
if not root:
return []
stack = [root]
res = []
while stack:
cur = stack.pop()
res.insert(0, cur.val)
if cur.left:
stack.append(cur.left)
if cur.right:
stack.append(cur.right)
return res
15. 三数之和 【Leetcode】Python实现三数之和_HelloWorld-CSDN博客https://blog.csdn.net/chenhua1125/article/details/80543379力扣https://leetcode-cn.com/problems/3sum/
class Solution(object):
def threeSum(self, nums):
"""
:type nums: List[int]
:rtype: List[List[int]]
"""
res = []
nums = sorted(nums)
for i in range(len(nums)):
if nums[i] > 0:
break
if i > 0 and nums[i] == nums[i-1]:
continue
left = i + 1
right = len(nums) -1
while left < right:
if nums[left] + nums[right] > - nums[i]:
right -= 1
elif nums[left] + nums[right] < -nums[i]:
left += 1
else:
res.append([nums[i],nums[left],nums[right]])
while left < right and nums[left] == nums[left+1]:
left += 1
while left < right and nums[right] == nums[right-1]:
right -= 1
left += 1
right -= 1
return res
三个指针,一个i指针,一对left和right指针,找i索引之后的值的和是否有等于i索引的负数。
但是我自己写的超时了,因为没有在找到相等的时候更新left和right指针以及舍弃掉重复的元素。
121. 买卖股票的最佳时机 力扣https://leetcode-cn.com/problems/best-time-to-buy-and-sell-stock/
class Solution(object):
def maxProfit(self, prices):
"""
:type prices: List[int]
:rtype: int
"""
res = 0
mins = prices[0]
for i in range(1,len(prices)):
if prices[i] < mins:
mins = prices[i]
res = max(res, prices[i] - mins)
if res > 0:
return res
else:
return 0
自己写还是写不出来。
160. 相交链表 力扣https://leetcode-cn.com/problems/intersection-of-two-linked-lists/
# Definition for singly-linked list.
# class ListNode(object):
# def __init__(self, x):
# self.val = x
# self.next = None
class Solution(object):
def getIntersectionNode(self, headA, headB):
"""
:type head1, head1: ListNode
:rtype: ListNode
"""
if headA is None or headB is None:
return None
pA, pB = headA, headB
while pA != pB: # 如果不相交,最多在各相互遍历一次后,一起走到None。
if pA is None:
pA = headB
else:
pA = pA.next
if pB is None:
pB = headA
else:
pB = pB.next
return pA
21. 合并两个有序链表 (腾讯面试)
class Solution(object):
def mergeTwoLists(self, l1, l2):
"""
:type l1: ListNode
:type l2: ListNode
:rtype: ListNode
"""
new = ListNode(None)
node = new
while l1 and l2:
if l1.val < l2.val:
node.next = l1
l1 = l1.next
else:
node.next = l2
l2 = l2.next
node = node.next
if l1:
node.next = l1
else:
node.next = l2
return new.next
class Solution(object):
def twoSum(self, nums, target):
"""
:type nums: List[int]
:type target: int
:rtype: List[int]
"""
dic = dict()
for index, num in enumerate(nums):
another_num = target - num
if another_num in dic:
return [dic[another_num], index]
dic[num] = index
return None
连两数之和都做不出来了。。。我脑子里觉得我两年之前做出来了,大概是梦里做出来了!
236. 二叉树的最近公共祖先 (不会)
LeetCode-Python-236. 二叉树的最近公共祖先_Keep Coding-CSDN博客
class Solution(object):
def lowestCommonAncestor(self, root, p, q):
"""
:type root: TreeNode
:type p: TreeNode
:type q: TreeNode
:rtype: TreeNode
"""
if not root or root == p or root == q:
return root
else:
left = self.lowestCommonAncestor(root.left, p, q)
right = self.lowestCommonAncestor(root.right, p, q)
if left and right: #一个在左子树,一个在右子树
return root
elif left:#都在左子树
return left
elif right:#都在右子树
return right
else:
return
二叉树要我狗命。
class Solution(object):
def maxSubArray(self, nums):
"""
:type nums: List[int]
:rtype: int
"""
#把nums中的每个元素换成截至到此元素最大连续子数组和
for i in range(1, len(nums)):
nums[i]= nums[i] + max(nums[i-1], 0)
return max(nums)
42. 接雨水 (高频题)
class Solution(object):
def trap(self, height):
"""
:type height: List[int]
:rtype: int
"""
if len(height) <= 1:
return 0
max_height = 0
max_height_index = 0
# 找到最高点
for i in range(len(height)):
h = height[i]
if h > max_height:
max_height = h
max_height_index = i
area = 0
# 从左边往最高点遍历
tmp = height[0]
for i in range(max_height_index):
if height[i] > tmp:
tmp = height[i]
else:
area = area + (tmp - height[i])
# 从右边往最高点遍历
tmp = height[-1]
for i in reversed(range(max_height_index + 1, len(height))):
if height[i] > tmp:
tmp = height[i]
else:
area = area + (tmp - height[i])
return area
class Solution(object):
def addStrings(self, num1, num2):
"""
:type num1: str
:type num2: str
:rtype: str
"""
tmp = 0
nums1 = list(num1)[::-1]
nums2 = list(num2)[::-1]
if len(nums1) > len(nums2):
nums2 = nums2 + [0] *(len(nums1)-len(nums2))
if len(nums2) > len(nums1):
nums1 = nums1 + [0] *(len(nums2)-len(nums1))
res = [0] * (len(nums1)+1)
for i in range(len(nums1)):
if int(nums1[i]) + int(nums2[i]) + tmp >= 10:
res[i] = str(int(nums1[i]) + int(nums2[i]) - 10 + tmp)
tmp = 1
else:
res[i] = str(int(nums1[i]) + int(nums2[i]) + tmp)
tmp = 0
if tmp == 1:
res[-1] = str(tmp)
else:
res.pop(-1)
return "".join(res[::-1])
自己写的,太麻烦了需要优化。
class Solution(object):
def merge(self, nums1, m, nums2, n):
"""
:type nums1: List[int]
:type m: int
:type nums2: List[int]
:type n: int
:rtype: None Do not return anything, modify nums1 in-place instead.
"""
temp = m+n-1
m -= 1
n -= 1
while m >= 0 and n>=0:
if nums1[m] >= nums2[n]:
nums1[temp] = nums1[m]
temp -= 1
m -= 1
else:
nums1[temp] = nums2[n]
temp -= 1
n-= 1
while n>=0:
nums1[temp] = nums2[n]
temp -= 1
n -= 1
return nums1
可真令人头秃。
199. 二叉树的右视图
class Solution(object):
def rightSideView(self, root):
"""
:type root: TreeNode
:rtype: List[int]
"""
if not root:
return []
queue=[root]
res=[]
cur=[]
while queue:
length=len(queue)
for i in range(0,length): #一个curcount循环是一层的结点
root=queue.pop(0)
cur.append(root.val)
if root.left:
queue.append(root.left)
if root.right:
queue.append(root.right)
res.append(cur[-1])
cur=[]
return res
其实就是二叉树层序遍历,取每层的最后一个结点罢了。
class Solution(object):
def search(self, nums, target):
"""
:type nums: List[int]
:type target: int
:rtype: int
"""
if len(nums) < 10:
for i in range(len(nums)):
if nums[i] == target:
return i
return -1
left = 0
right = len(nums) - 1
if target >= nums[0]:
while left < right:
if nums[left] > nums[left+1]:
if nums[left] == target:
return left
elif nums[left+1] == target:
return left + 1
else:
return -1
if nums[left] == target:
return left
else:
left+=1
if target <= nums[-1]:
while left < right:
if nums[right] < nums[right-1]:
if nums[right] == target:
return right
elif nums[right+1] == target:
return right + 1
else:
return -1
if nums[right] == target:
return right
else:
right -=1
if target<nums[0] and target>nums[-1]:
return -1
边界条件令人头疼,索性10个内的遍历。
class Solution(object):
def numIslands(self, grid):
m, n = len(grid), len(grid[0])
ans = 0
def dfs(i, j):
if 0 <= i < m and 0 <= j < n and grid[i][j] == '1':
grid[i][j] = '0'
dfs(i + 1, j)
dfs(i - 1, j)
dfs(i, j - 1)
dfs(i, j + 1)
for i in range(m):
for j in range(n):
if grid[i][j] == '1':
ans += 1
dfs(i, j)
return ans
深度优先搜索。遇到这种矩阵问题,就有(1,0)(0,1)(-1,0)(0,-1)。
class Solution(object):
def spiralOrder(self, matrix):
"""
:type matrix: List[List[int]]
:rtype: List[int]
"""
if not matrix:
return None
m, n = len(matrix), len(matrix[0])
# 顺时针方向(右下左上)
dm = [0, 1, 0, -1]
dn = [1, 0, -1, 0]
di = 0 # 方向指针
res = []
x = y = 0 # 位置
for _ in range(m*n): # 最多步长 m*n
res.append(matrix[x][y])
matrix[x][y] = 'v' # 访问过标记为 'v'(‘visited’)
# 下一步位置
x_temp = x + dm[di]
y_temp = y + dn[di]
# 判断下一步位置是否合理,若合理则更新位置,若不合理则改变方向并更新位置
if 0<=x_temp<m and 0<=y_temp<n and matrix[x_temp][y_temp]!='v':
x, y = x_temp, y_temp
else:
di = (di+1) % 4
x += dm[di]
y += dn[di]
return res