1.list out of index
1.1寻址超出列表长度,例如 list=[1,2,3] ,但是寻址list[3]就会出现上述错误,
初始化列表 [0]*n 或者 [0 for i in range(n+1)]
2.某个函数 is not define
2.1 例如 class -- def name(self,--)
则在该函数中应用时应该用self.name
斐波那契数列:
解法一: 利用递归暴力求解
class Solution:
def fib(self, n: int) -> int:
if n<0:
return false
if n==0 or n==1:
return n
return self.fib(n-1)+self.fib(n-2)
解法二:利用f 存储已经计算出来的内容,并创建新的函数调用函数来循环 更改f ,
!!!什么时候需要自己再重新写一个函数:当某个函数会对除函数之外的东西造成改变,而哪个东西最后需要调用或者初始化,那么需要自己在函数内再写一个函数,并在一层函数中考虑初始化和输出参数
class Solution:
def fib(self, n: int) -> int:
f = [0 for _ in range(n+1)]
# print(f)
def help(list,n):
# 写这个函数的目的是根据已经存在的f和n求出f[n]的值,因此return 的应该是f[n]的值
if n==0 or n==1:
return n
if f[n] != 0:
return f[n]
f[n] = help(f,n-1)+help(f,n-2)
return f[n]
help(f,n)
return f[n]
也可以不用f,这里用到闭包的概念,函数中调用函数如果使用外部函数的变量那相当于有一个外部变量存储空间
class Solution:
def fib(self, n: int) -> int:
f = [0 for _ in range(n+1)]
# print(f)
def help(n):
# 写这个函数的目的是根据已经存在的f和n求出f[n]的值,因此return 的应该是f[n]的值
if n==0 or n==1:
return n
if f[n] != 0:
return f[n]
f[n] = help(n-1)+help(n-2)
return f[n]
help(n)
return f[n]
方法三:
class Solution:
def fib(self, n: int) -> int:
f = [0 for _ in range(n+1)]
if n < 1:
return False
# base case
f[1]=1
f[2]=1
# 构造函数
for i in range(2,n+1):
f[i] = f[i-1]+f[i-2]
print(f)
# 取值
return f[n]
解法四:
int fib(int n) {
if (n == 0 || n == 1) {
// base case
return n;
}
// 分别代表 dp[i - 1] 和 dp[i - 2]
int dp_i_1 = 1, dp_i_2 = 0;
for (int i = 2; i <= n; i++) {
// dp[i] = dp[i - 1] + dp[i - 2];
int dp_i = dp_i_1 + dp_i_2;
// 滚动更新
dp_i_2 = dp_i_1;
dp_i_1 = dp_i;
}
return dp_i_1;
}
凑零钱
BBQ了,这题想不清楚哇
class Solution:
def coinChange(self, coins: List[int], amount: int) -> int:
dp=[amount+1 for _ in range(amount+1)]
dp[0]=0
for i in range(1,amount+1):
for coin in coins:
if i-coin<0:
continue
dp[i]=min(dp[i],1+dp[i-coin])
if dp[amount]==amount+1:
return -1
else:
return dp[amount]
记录错误思路
class Solution:
def coinChange(self, coins: List[int], amount: int) -> int:
# 思路:从下往上:把所有凑法搞出来最后和amount比较,大小相同就可以,最后留下硬币书最少的情况---不可实现
# 从上往下,amount - coin[i] 能用几个硬币实现,最终+1
# 由于有最终需要返回的res,并且res需要多次比较,所以需要写一个新函数
res = amount+1
temp = 0
reslist = []
reslist1 = []
# 思路漏了一点哇 救命,这个直接算是不是要有一个进入和一个推出
def coinhelp(coins,amount,temp):
#这一点没想清楚
#比如一个 temp 我的思路是每次调用传递一个temp,temp 每次调用都会更改,在amount =0 的时候对比temp 和 res ,再把temp 置为 0
nonlocal res,reslist,reslist1
for i in coins:
amounttmp = amount - i
temp += 1
reslist.append(i)
if amounttmp<0:
continue
if amounttmp == 0:
res = min(res,temp)
print(temp,reslist)
reslist1.append(reslist)
reslist.remove(i)
amounttmp+=i
continue
coinhelp(coins,amounttmp,temp)
coinhelp(coins,amount,temp)
return res
class Solution:
def coinChange(self, coins: List[int], amount: int) -> int:
res = 10000
temp = 0
# reslist = []
templist = []
def coinhelp(coins,amount):
nonlocal res,temp,templist
# 写了个全排列我靠真是离了谱了
for i in coins:
if amount<0:
continue
if amount == 0:
# reslist.append(templist)
print(templist)
yaya = temp
temp =0
templist = []
res = min(res,yaya)
continue
# print(i)
amount = amount -i
templist.append(i)
print(templist)
temp+=1
coinhelp(coins,amount)
temp -= 1
amount = amount +i
if len(templist)>0:
templist.pop()
coinhelp(coins,amount)
return res
3.list.append(list) 和 list.append(list[:])的问题
在写全排列的时候,
# class TreeNode:
# def __init__(self, x):
# self.val = x
# self.left = None
# self.right = None
#
# 代码中的类名、方法名、参数名已经指定,请勿修改,直接返回方法规定的值即可
#
#
# @param root TreeNode类
# @param target int整型
# @return int整型二维数组
#
class Solution:
def FindPath(self , root: TreeNode, target: int) -> List[List[int]]:
# write code here
if not root or not target:
return None
list_all = []
list_temp = []
temp_target = 0
def traverse(root,temp_target,target):
# nonlocal list_all
if not root:
return
temp_target += root.val
list_temp.append(root.val)
print(root.val)
if temp_target == target and not root.left and not root.right:
# list_all.append(list_temp[:])
list_all.append(list_temp[:])
print('temp',list_temp)
print(id(list_temp))
print('list_all',list_all)
print(id(list_all))
if root.left:
traverse(root.left,temp_target,target)
if root.right:
traverse(root.right,temp_target,target)
print('before',list_temp,temp_target)
temp_target -= root.val
list_temp.remove(root.val)
print('after',list_temp,temp_target)
traverse(root,temp_target,target)
return list_all
使用 list.append(list) 得到
1 . temp [10, 5, 7]
list_all [[10, 5, 7]]
2 . temp [10, 12]
list_all [[10, 12], [10, 12]]
3 . [[],[]]
错误原因: temp 每次都指向同一个位置,后面改变数据,覆盖了前面的数据。
而使用list.append(list[:]) 或者 list_all.append(list(list_temp))得到
1. temp [10, 5, 7]
list_all [[10, 5, 7]]
2. temp [10, 12]
list_all [[10, 5, 7], [10, 12]]
3. list_all [[10, 5, 7], [10, 12]]
(5条消息) 列表的append()操作和list()函数对应的copy关系_xx_xjm的博客-CSDN博客_append list
python的list赋值方法-浅拷贝与赋值 - JavaShuo
list.append()没有进行复制,而是进行引用,
浅拷贝只拷贝数组的一层 - 建立新对象,内容是对原对象的引用- list1 = list(list2) list1 = list2[:] list1 =copy.copy(list2) 浅拷贝产生的list1再也不是list2了,使用is能够发现他们不是同一个对象,使用id查看,发现它们也不指向同一片内存。可是当咱们使用 id(x) for x in a 和 id(x) for x in b 时,能够看到两者包含的元素的地址是相同的。
深拷贝进行多层拷贝 --
浅拷贝对应,深拷贝拷贝了对象的全部元素,包括多层嵌套的元素。于是,它的时间和空间开销要高。一样对a,若使用b = copy.deepcopy(a),再修改b将不会影响到a了。即便嵌套的列表具备更深的层次,也不会产生任何影响,由于深拷贝出来的对象根本就是一个全新的对象,再也不与原来的对象有任何关联
移位操作
。