我试图找到一个数字的所有主要除数。我正在尝试不传递空列表作为参数。
我可以在没有空列表参数的情况下调用函数podz,但是结果不正确-这是第一个问题-为什么? 我在podzb函数中得到了正确的结果,但是有必要提供空列表参数。
代码:
def podz(x, lista = ()):
# xa = []
lis = list(lista)
# lis = list(lista) # czemu to psuje wynik? jak odpalić krok po kroku?
# print(lis)
for i in range(2, x + 1):
# print(f'x: {x}')
# print(f'i: {i}')
# print(f'lis: {lis}')
if x % i == 0:
lis.append(i)
# print(f'lis2: {lis}')
podz(int(x / i), lis)
break
return(lis)
def podzb(x, lista = ()):
# xa = []
lis = lista
# lis = list(lista) # czemu to psuje wynik? jak odpalić krok po kroku?
# print(lis)
for i in range(2, x + 1):
# print(f'x: {x}')
# print(f'i: {i}')
# print(f'lis: {lis}')
if x % i == 0:
lis.append(i)
# print(f'lis2: {lis}')
podzb(int(x / i), lis)
break
return(lis)
a = podz(50, [])
print(f'a: {a}')
aa = podz(50)
print(f'aa: {aa}')
a2 = podzb(50, [])
print(f'a2: {a2}')
# aa = podzb(50) #this causes: AttributeError: 'tuple' object has no attribute 'append'
# print(f'aa: {aa}')
答案 0 :(得分:1)
AttributeError
的原因是默认参数是一个空元组()
,而不是一个空列表[]
。现在,您可以选择不使用空列表作为various reasons的默认参数,但是由于您要对该对象进行突变,因此确实需要一个列表。
解决方案是做类似的事情
def podzb(x, lista=None):
if lista is None:
lista = []
... # rest of function
答案 1 :(得分:1)
执行时:
lis = list(lista)
您复制列表。因此,您无需修改它。
答案 2 :(得分:1)
在podz
中,这里:
lis = list(lista)
您根据lista
的内容创建一个新列表。然后,您在此处进行递归调用时传递此新列表:
if x % i == 0:
lis.append(i)
# print(f'lis2: {lis}')
podz(int(x / i), lis)
因此,在递归调用中,您将再次创建一个新列表并将其追加到列表中,然后在递归调用返回时丢弃此新列表,并且由于递归调用在第一个列表的副本上起作用,因此第一个列表是也不更新。
要执行此操作,您必须将递归调用的结果添加到第一个列表中:
if x % i == 0:
lis.append(i)
# print(f'lis2: {lis}')
lis.extend(podz(int(x / i), lis))
第二个版本(podzb
)不会复制该列表,因此它是由所有递归调用更新的同一列表。
答案 3 :(得分:0)
这是因为您从未更新过除数列表,而是将其传递给随后的函数调用,在该函数中创建了一个新列表(然后返回),但从未捕获过返回值。实际上,您根本不需要tuple
/ list
参数,您可以简单地计算并返回函数中的除数,例如:
def podz(x):
div = []
for i in range(2, x + 1):
if x % i == 0:
div.append(i)
div.extend(podz(int(x / i)))
break
return div
答案 4 :(得分:0)
您的代码有点混乱。 这是给您的更干净的代码:
def divisors(num):
divisors = []
for divisor in range(2, num + 1):
if num % divisor == 0 and isPrime(divisor):
divisors.append(divisor)
return divisors
def isPrime(num):
for divisor in range(2, num):
if num % divisor == 0: return False
return True
a = divisors(50)
print(f'a: {a}')