2011-12-25 74 views
10

我已经从我延伸的模块清理一些代码,我似乎无法找到一种方法来Pythonify此代码:计数类的实例?

global_next_id = 1 

class Obj: 
    def __init__(self): 
    global global_next_id 
    self.id = global_next_id 

    global_next_id += 1 

该代码使用全局ID来跟踪实例(我在内部也需要变量self.id,它需要是一个数字)。

任何人都可以提出一种方法来Pythonify这段代码吗?

+1

为什么你需要“跟踪类的实例的”具有全球ID? – 2011-12-25 04:46:47

+1

这是我正在修改的PDF库。每个PDF'Obj'都需要打印出各自的ID。 – Blender 2011-12-25 06:45:10

回答

34

尝试这样:

from itertools import count 

class Obj(object): 
    _ids = count(0) 

    def __init__(self): 
    self.id = next(self._ids) 
+1

我完全忽略了类的变量......感谢'itertools'解决方案! – Blender 2011-12-25 04:03:03

+1

我希望我可以声称自己的信用 - 我在另一篇文章的某处看到它。它的优雅和高效。 – 2011-12-25 04:09:47

+0

呃,它适合我。 – Blender 2011-12-25 04:17:41

1

发电机?

def get_next_id(): 
    curr_id = 1 
    while True: 
     yield curr_id 
     curr_id += 1 
3

这里是一个方法来计数没有后代类共享相同的ID /计数的实例。元类用于为每个类创建一个单独的id计数器。

Metaclasses使用Python 3语法。

import itertools 

class InstanceCounterMeta(type): 
    """ Metaclass to make instance counter not share count with descendants 
    """ 
    def __init__(cls, name, bases, attrs): 
     super().__init__(name, bases, attrs) 
     cls._ids = itertools.count(1) 

class InstanceCounter(object, metaclass=InstanceCounterMeta): 
    """ Mixin to add automatic ID generation 
    """ 
    def __init__(self): 
     self.id = next(self.__class__._ids) 
0

这应该做的工作:

​​