我正在尝试将任意长度的字符串拆分为3个字符的块。我知道之前已经问过这个问题(How do you split a list into evenly sized chunks?),但是这个答案解决了列表理解的问题;我试图使用递归函数调用来解决问题,所以我的问题更多是关于Python中的递归函数调用。
我的功能正常工作,直到“基本情况”,最后一个3个或更少字符的字符串。我收到TypeError: can only concatenate list (not "NoneType") to list
。
为什么基本案例会返回None
而不是list
?我在基本情况下显式创建一个名为final_value
的列表并返回该列表。我甚至有一个调试print语句,它向我显示基本案例返回值的类型为<class 'list'>
。
我的代码如下。
three_char_strings = []
def split3(str):
if len(str) <= 3:
final_value = []
final_value.append(str)
print('Final value: %s\nFinal value type: %s\n' % (final_value, type(final_value))) #For debugging
return final_value
else:
beginning = str[0:3]
three_char_strings.append(beginning)
remaining = str[3:]
three_char_strings + split3(remaining)
答案 0 :(得分:3)
你有两个问题:
基本情况下仅 return
,因此另一种情况将隐含return None
;以及
您不会在基本情况下改变three_char_strings
。事实上,目前尚不清楚为什么要实现这一点来改变所有的外部列表,因为如果你需要再次调用它会导致问题。
你可能应该做的事情如下:
def split3(str):
if len(str) <= 3:
return [str]
else:
beginning = str[:3]
remaining = str[3:]
return [beginning] + split3(remaining)
当你调用这个函数时,你想要的是什么,没有依赖three_char_list
列表在范围内并且为空:
>>> split3('abcdefghijklmnopqrstuvwxyz')
['abc', 'def', 'ghi', 'jkl', 'mno', 'pqr', 'stu', 'vwx', 'yz']
这种方法的缺点是它创建了几个列表。如果你想要每个顶级呼叫一个列表,你可以做例如:
def split3(str, out=None):
if out is None:
out = []
out.append(str[:3])
if len(str) > 3:
split3(str[3:], out)
return out
如果您想知道为什么out=None
,请参阅"Least Astonishment" and the Mutable Default Argument。
答案 1 :(得分:2)
虽然最初的问题是您的非基本情况没有return
声明(意味着它隐式返回None
),但看看如何代码可以在Python中简化
def split3(s):
return [s] if len(s) <= 3 else [s[:3]] + split3(s[3:])