Python命名元组列表,替换属性

scr*_*ate 4 python list namedtuple

这是一些简化的代码,我不明白为什么它不起作用.

from collections import namedtuple

MyStruct = namedtuple('MyStruct', 'ThreadInstance ThreadName Mnemonic IpAddr IpGW Status Mode')

Node = MyStruct(None, '', '', '', '',  -1, 0)
NodeDb = []
for id in range(4):
    NodeDb.append(Node)

NodeDb[2]._replace(ThreadName='T2')
NodeDb[2]._replace(Mnemonic='ABCD')
NodeDb[2]._replace(IpAddr='192.0.1.2')
NodeDb[2]._replace(IpGW='192.0.1.3')
NodeDb[2]._replace(Status=0)
NodeDb[2]._replace(Mode=2)

print(NodeDb)
Run Code Online (Sandbox Code Playgroud)

这是输出

'>>>
[MyStruct(ThreadInstance=None, ThreadName='', Mnemonic='', IpAddr='', IpGW='', Status=-1, Mode=0),
 MyStruct(ThreadInstance=None, ThreadName='', Mnemonic='', IpAddr='', IpGW='', Status=-1, Mode=0), 
 MyStruct(ThreadInstance=None, ThreadName='', Mnemonic='', IpAddr='', IpGW='', Status=-1, Mode=0), 
 MyStruct(ThreadInstance=None, ThreadName='', Mnemonic='', IpAddr='', IpGW='', Status=-1, Mode=0)]'
Run Code Online (Sandbox Code Playgroud)

Rob*_*ers 7

_replace不会做你认为它做的事情.来自文档:

somenamedtuple._replace(kwargs)

返回使用新值替换指定字段的命名元组的新实例:

>>> p = Point(x=11, y=22)  
>>> p._replace(x=33)  
Point(x=33, y=22)
Run Code Online (Sandbox Code Playgroud)

你正在打电话,_replace但你永远不会存储新的Node返回.它返回一个新对象而不是改变对象"就地"的原因namedtuples是根据定义是不可变的,即在创建它们之后它们不能被更改.

请注意,您的for循环会创建一个包含四个相同引用的列表Node.在这种情况下,这不是一个真正的问题,因为您创建的对象都是相同的并且namedtuple是不可变的,但通常要注意这一点.

总结如下:

from collections import namedtuple

MyStruct = namedtuple('MyStruct', 'ThreadInstance ThreadName Mnemonic IpAddr IpGW Status Mode')

NodeDb = []
Node = MyStruct(None, '', '', '', '',  -1, 0)
for id in range(4):
    NodeDb.append(Node)

NodeDb[2] = NodeDb[2]._replace(ThreadName='T2',
                               Mnemonic='ABCD',
                               IpAddr='192.0.1.2',
                               IpGW='192.0.1.3',
                               Status=0,
                               Mode=2)

print(NodeDb)
Run Code Online (Sandbox Code Playgroud)