蟒发生器VS理解并通过引用传递VS值(Python generator vs comprehensi

2019-11-03 11:30发布

我有一些代码,遍历字符串,并产生从字符串对象,我打电话给一个实例的列表。 它看起来是这样的。

from collections import defaultdict

class MyInstance:
    data = defaultdict(str)

    def __init__(self, data, parser):
        # parse the input
        self.parser = parser


class MyParser:
    def __init__(self, data):
        self.data = data
        data = data.split('\n\n')
        self.instances = (MyInstance(instance, self) for instance in data)


mydata = # ... coming in from stdin or file
parser = MyParser(mydata)

这是工作正常,但后来我意识到我需要检查我的情况不止一次。 所以,我想我会只是改变了我的生成器列表理解:

self.instances = [MyInstance(instance, self) for instance in data]

这让我我的情况下,迭代的次数为想要的,但突然之间,所有的情况都是一样的。 当我这行之前打印出来的数据,每个实例是唯一的。 然而,列表理解后,他们都是一样的。

class MyParser:
    def __init__(self, data):
        self.data = data
        data = data.split('\n\n')
        print data
        self.instances = (MyInstance(instance, self) for instance in data)
        print list(self.instances)

打印...

['the soldier sleeps', 'the big soldier sleeps', 'the big wonderful soldier sleeps']
['the big wonderful soldier sleeps', 'the big wonderful soldier sleeps', 'the big wonderful soldier sleeps']

然而,奇怪的是,当我试图重新使用类似的代码上面的这个问题, 我不能复制它

class myClass:

  def __init__(self, i):
    self.i = i

  def __repr__(self):
    return self.__str__()

  def __str__(self):
    return str(self.i)


instances = [myClass(i) for i in range(3)]
print instances

instances = (myClass(i) for i in range(3))
print list(instances)

打印...

[0, 1, 2]
[0, 1, 2]

我检查,看看是否每个实例的内存地址(以断码)是相同或不同的,而且看起来它们是不同的......(虽然我承认我不知道这意味着什么)

for i in self.instances:
  print id(i) # 4463026760, 4463026544, 4463026616

所以,我不知道发生了什么事情。 为什么这些情况似乎有什么建议要链接?

Answer 1:

看来,这个问题与我是如何开始我的数据做。 我发起defaultdict作为类中的一员:

class myClass:
    self.data = defaultdict(str)

    def __init__(self, data):
        for i, instance in enumerate(data.split('\n')):
            # Do something...
            self.data[i] = instance

我改成了这样:

class myClass:

    def __init__(self, data):
        self.data = defaultdict(str)
        for i, instance in enumerate(data.split('\n')):
            # Do something...
            self.data[i] = instance

这固定我的问题。 有兴趣听,如果有人知道这是为什么。



文章来源: Python generator vs comprehension and pass by reference vs value