我正在学习Python,我正在处理Mutable Default Argument问题.
# BAD: if `a_list` is not passed in, the default will wrongly retain its contents between successive function calls
def bad_append(new_item, a_list=[]):
a_list.append(new_item)
return a_list
# GOOD: if `a_list` is not passed in, the default will always correctly be []
def good_append(new_item, a_list=None):
if a_list is None:
a_list = []
a_list.append(new_item)
return a_list
Run Code Online (Sandbox Code Playgroud)
我知道a_list只有在def第一次遇到语句时才初始化,这就是为什么后续调用bad_append使用相同的列表对象的原因.
我不明白的是为什么good_append有所不同.它看起来像a_list会仍然只初始化一次; 因此,该if语句仅在第一次调用函数时才为真,这意味着a_list只会[]在第一次调用时重置,这意味着它仍然会累积所有过去的new_item …
例如,我有一个基本方法,它将返回一个排列列表.
import itertools
def perms(elements, set_length=elements):
data=[]
for x in range(elements):
data.append(x+1)
return list(itertools.permutations(data, set_length))
Run Code Online (Sandbox Code Playgroud)
现在我理解,在当前状态下,这段代码不会运行,因为第二段elements没有定义,但是有没有优雅的方法来完成我在这里尝试做的事情?如果仍然不清楚,我想使默认setLength值等于传入的第一个参数.谢谢.
有人可以向我解释下面的代码.
class InnerTest:
def __init__(self, value = 0):
self.value = value
class OuterTest:
def __init__(self, inner_test = InnerTest()):
self.inner_test = inner_test
a = OuterTest()
b = OuterTest()
a.inner_test.value = 42
print b.inner_test.value
Run Code Online (Sandbox Code Playgroud)
它打印42,我预计0.
我打算创建两个OuterTest实例,每个实例都包含一个不同的InnerTest实例.相反,我得到了两个引用同一个InnerTest实例的OuterTest实例.
还有什么是正确的方法来实现我想要的东西?
在 Python 中处理可变默认参数的方法是将它们设置为 None。
例如:
def foo(bar=None):
bar = [] if bar is None else bar
return sorted(bar)
Run Code Online (Sandbox Code Playgroud)
如果我输入函数定义,那么唯一的类型 forbar说的bar是Optional,很明显,它不是Optional我期望sorted在其上运行该函数的时间:
def foo(bar: Optional[List[int]]=None):
bar = [] if bar is None else bar
return sorted(bar) # bar cannot be `None` here
Run Code Online (Sandbox Code Playgroud)
那么我应该投吗?
def foo(bar: Optional[List[int]]=None):
bar = [] if bar is None else bar
bar = cast(List[int], bar) # make it explicit that `bar` cannot be `None`
return sorted(bar) …Run Code Online (Sandbox Code Playgroud) 我在New-Style Classes中发现了子类化和字典更新的一个奇怪问题:
Python 2.6.2 (r262:71605, Apr 14 2009, 22:40:02) [MSC v.1500 32 bit (Intel)] on
win32
>>> class a(object):
... def __init__(self, props={}):
... self.props = props
...
>>> class b(a):
... def __init__(self, val = None):
... super(b, self).__init__()
... self.props.update({'arg': val})
...
>>> class c(b):
... def __init__(self, val):
... super(c, self).__init__(val)
...
>>> b_inst = b(2)
>>> b_inst.props
{'arg': 2}
>>> c_inst = c(3)
>>> c_inst.props
{'arg': 3}
>>> b_inst.props
{'arg': 3}
>>>
Run Code Online (Sandbox Code Playgroud)
在debug中,在第二个call(c(3))中,您可以看到a …
我很难理解类init的参数会发生什么,
例如:
class A(object):
def __init__(self, argument=[]):
self.argument = argument[:]
Run Code Online (Sandbox Code Playgroud)
要么:
def __init__(self,argument=None):
self.arguments = arguments or []
Run Code Online (Sandbox Code Playgroud)
要么:
def __init__(self, argument=[]):
self.argument = argument
Run Code Online (Sandbox Code Playgroud)
这是不可能的,因为每个A对象的默认值都指向同一块内存.我真的不明白这里发生了什么以及它是如何发生的.
我正在使用以下方式读取文件:
def readFile():
file = open('Rules.txt', 'r')
lines = file.readlines()
for line in lines:
rulesList.append(line)
Run Code Online (Sandbox Code Playgroud)
规则列表:
['\n', "Rule(F1, HTTPS TCP, ['ip', 'ip'], ['www.google.ca', '8.8.8.8'], 443)\n", '\n', "Rule(F2, HTTPS TCP, ['ip', 'ip'], ['75.2.18.233'], 443)\n", '\n']
Run Code Online (Sandbox Code Playgroud)
我的文件如下所示:
Rule(F1, HTTPS TCP, ['ip', 'ip'], ['www.google.ca', '8.8.8.8'], 443)
Rule(F2, HTTPS TCP, ['ip', 'ip'], ['ip'], 443)
Run Code Online (Sandbox Code Playgroud)
我想将这些值提供给我创建的类
class Rule:
def __init__(self, flowNumber, protocol, port, fromIP=[], toIP=[]):
self.flowNumber = flowNumber
self.protocol = protocol
self.port = port
self.fromIP = fromIP
self.toIP = toIP
def __repr__(self):
return f'\nRule({self.flowNumber}, {self.protocol}, …Run Code Online (Sandbox Code Playgroud) 每次打电话给我时,我都想尝试新的随机名称.我把它定义为
def namemethod():
return ''.join(random.choice(string.lowercase) for x in range(5))
class Test(object):
def __init__(self, name=namemethod()):
self.name = name
Run Code Online (Sandbox Code Playgroud)
我正在Test通过for循环来调用类获取新名称,但我一直得到相同的名称,是不是假设调用init方法并获得新的随机名称?
for i in range(5):
person = Test()
print person.name
Run Code Online (Sandbox Code Playgroud)
为什么person = Test()不namemethod每次都打电话?
我正在编写这段代码作为面向对象编程的练习.
在这里,我试图将房屋定义为房间列表,并将每个房间定义为设备列表(例如灯具).
首先,我创建了所有对象,并将两个房间附加到房屋,并为每个房间添加了不同的设备.很基本的.
问题是,似乎设备被附加到两个房间.这是为什么?
代码:
#! /usr/bin/python
class House:
def __init__(self, rooms = list()):
self.rooms = rooms
print('house created')
class Room:
def __init__(self, name = 'a room', devs = list()):
self.name = name
self.devs = devs
print('room ' + self.name + ' created')
class Device:
def __init__(self, name = 'a device'):
self.name = name
print('device ' + self.name + ' created')
def main():
#1
h = House()
r1 = Room(name = 'R1')
r2 = Room(name = 'R2')
d1 = Device(name …Run Code Online (Sandbox Code Playgroud) class A:
def __init__(self, n=[0]):
self.data = n
a = A()
print a.data[0] #print 0
a.data[0] +=1
b = A()
print a.data[0] #print 1, desired output is 0
Run Code Online (Sandbox Code Playgroud)
在上面的例子中,有没有办法在__init __()类A中提供带有可变对象(如列表或类)的默认参数,但是b不受操作a的影响?