给定一个整数数组 nums 和一个整数目标值 target,请你在该数组中找出 和为目标值 target 的那 两个 整数,并返回它们的数组下标。
你可以假设每种输入只会对应一个答案。但是,数组中同一个元素在答案里不能重复出现。
你可以按任意顺序返回答案
输入:nums = [2,7,11,15], target = 9
输出:[0,1]
解释:因为 nums[0] + nums[1] == 9 ,返回 [0, 1] 。
思路:用字典,一边存一边找
时间复杂度和空间复杂度都为O(n)
class Solution:
def twoSum(self, nums: List[int], target: int) -> List[int]:
dic={
}
for i in range(len(nums)):
if (target-nums[i]) in dic.keys():
return [i,dic[target-nums[i]]]
else:
dic[nums[i]] = i
给定一个只包括 ‘(’,‘)’,‘{’,‘}’,‘[’,‘]’ 的字符串 s ,判断字符串是否有效。
有效字符串需满足:
左括号必须用相同类型的右括号闭合。
左括号必须以正确的顺序闭合。
每个右括号都有一个对应的相同类型的左括号。
示例 1:
输入:s = "()"
输出:true
示例 2:
输入:s = "()[]{}"
输出:true
示例 3:
输入:s = "(]"
输出:false
提示:([)]为false,({[]})为true
#有左括号存,有右括号取,时间复杂度和空间复杂度都为O(n)
class Solution:
def isValid(self, s: str) -> bool:
if len(s)%2==1:
return False
tmp=[]
dic={
')':'(','}':'{',']':'['}
for i in s:
if i in "([{":
tmp.append(i)
else:
#没得可取的情况
if len(tmp)==0:
return False
elif dic[i] == tmp[-1]:
tmp.pop()
else:
return False
if len(tmp)>0:
return False
else:
return True
#暴力替换
class Solution:
def isValid(self, s: str) -> bool:
while '{}' in s or '()' in s or '[]' in s:
s = s.replace('{}', '')
s = s.replace('[]', '')
s = s.replace('()', '')
return s == ''
将两个升序链表合并为一个新的 升序 链表并返回。新链表是通过拼接给定的两个链表的所有节点组成的。
输入:l1 = [1,2,4], l2 = [1,3,4]
输出:[1,1,2,3,4,4]
思路:用递归,当甩手掌柜,时间复杂度O(n)
# Definition for singly-linked list.
# class ListNode:
# def __init__(self, val=0, next=None):
# self.val = val
# self.next = next
class Solution:
def mergeTwoLists(self, list1: Optional[ListNode], list2: Optional[ListNode]) -> Optional[ListNode]:
#list1没了返回list2
if not list1:return list2
#list2没了返回list1
if not list2:return list1
#如果当前list1的值比较小,确定当前的值为list1,下一个值就比较list1.next和list2
if list1.val<=list2.val:
list1.next=self.mergeTwoLists(list1.next,list2)
return list1
else:
list2.next=self.mergeTwoLists(list1,list2.next)
return list2
假设你正在爬楼梯。需要 n 阶你才能到达楼顶。
每次你可以爬 1 或 2 个台阶。你有多少种不同的方法可以爬到楼顶呢?
示例 1:
输入:n = 2
输出:2
解释:有两种方法可以爬到楼顶。
1. 1 阶 + 1 阶
2. 2 阶
示例 2:
输入:n = 3
输出:3
解释:有三种方法可以爬到楼顶。
1. 1 阶 + 1 阶 + 1 阶
2. 1 阶 + 2 阶
3. 2 阶 + 1 阶
思路:n=(n-1)+(n-2),因为迈到该台阶可以迈一步或者两步,符合斐波那契数列,[1,1,2,3,…],时间复杂度和空间复杂度O(n)
#斐波那契数列
class Solution:
def climbStairs(self, n: int) -> int:
if n==1:
return 1
res = [1,2]
while len(res)<n:
res.append(res[-1]+res[-2])
return res[-1]
给你一个 非空 整数数组 nums ,除了某个元素只出现一次以外,其余每个元素均出现两次。找出那个只出现了一次的元素。
你必须设计并实现线性时间复杂度的算法来解决此问题,且该算法只使用常量额外空间。
示例 1 :
输入:nums = [2,2,1]
输出:1
示例 2 :
输入:nums = [4,1,2,1,2]
输出:4
示例 3 :
输入:nums = [1]
输出:1
思路:异或。
异或运算有以下三个性质。
class Solution:
def singleNumber(self, nums: List[int]) -> int:
return reduce(lambda x,y:x^y,nums)
reduce用法:
from functools import reduce
def add(x, y) : # 两数相加
return x + y
sum1 = reduce(add, [1,2,3,4,5]) # 计算列表和:1+2+3+4+5
sum2 = reduce(lambda x, y: x+y, [1,2,3,4,5]) # 使用 lambda 匿名函数
print(sum1)
print(sum2)
给定一个数组 nums,编写一个函数将所有 0 移动到数组的末尾,同时保持非零元素的相对顺序。
请注意 ,必须在不复制数组的情况下原地对数组进行操作。
#不讲武德的做法
class Solution:
def moveZeroes(self, nums: List[int]) -> None:
"""
Do not return anything, modify nums in-place instead.
"""
n = nums.count(0)
for i in range(n):
nums.remove(0)
nums.append(0)
#双指针
#时间复杂度: O(n)
#空间复杂度: O(1)
#[0,1,0,3,12] [1,1,0,3,12] [1,3,0,3,12] [1,3,12,3,12] [1,3,12,0,0]
class Solution:
def moveZeroes(self, nums) -> None:
"""
Do not return anything, modify nums in-place instead.
"""
if not nums:
return 0
# 第一次遍历的时候,j指针记录非0的个数,只要是非0的统统都赋给nums[j]
j = 0
for i in range(len(nums)):
if nums[i]:
nums[j] = nums[i]
j += 1
# 非0元素统计完了,剩下的都是0了
# 所以第二次遍历把末尾的元素都赋为0即可
for i in range(j, len(nums)):
nums[i] = 0
#一次遍历,使用两个指针i和j,只要nums[i]!=0,我们就交换nums[i]和nums[j]
#时间复杂度: O(n)
#空间复杂度: O(1)
#[0,1,0,3,12] [1,0,0,3,12] [1,3,0,0,12] [1,3,12,0,0]
class Solution:
def moveZeroes(self, nums) -> None:
"""
Do not return anything, modify nums in-place instead.
"""
if not nums:
return 0
# 两个指针i和j
j = 0
for i in range(len(nums)):
# 当前元素!=0,就把其交换到左边,等于0的交换到右边
if nums[i]:
nums[j], nums[i] = nums[i], nums[j]
j += 1
二叉树的前中后遍历参考:
https://blog.csdn.net/qq_32482645/article/details/124915969
https://zhuanlan.zhihu.com/p/485397193
#递归
class Solution:
def inorderTraversal(self