0

更多地挖掘莳萝。特别是 detect.at 方法,它调用:

def _locate_object(address, module=None):
    """get object located at the given memory address (inverse of id(obj))"""
    special = [None, True, False] #XXX: more...?
    for obj in special:
        if address == id(obj): return obj
    if module:
        if PY3:
            objects = iter(module.__dict__.values())
        else:
            objects = module.__dict__.itervalues()
    else: objects = iter(gc.get_objects())
    for obj in objects:
        if address == id(obj): return obj
    # all bad below... nothing found so throw ReferenceError or TypeError
    from weakref import ReferenceError
    try: address = hex(address)
    except TypeError:
        raise TypeError("'%s' is not a valid memory address" % str(address))
    raise ReferenceError("Cannot reference object at '%s'" % address)

为什么我无法“获取”似乎位于地址的字符串对象:4332529152

>>> class Parent():
...     name="Big Papa"
...     def get_hitched(partner):
...             return name + "+" + partner + "TLFE"
... 
>>> johnny = Parent()
    >>> johnny = Parent()
>>> johnny.get_hitched("Mary")
'Big Papa + Mary TLFE'
>>> billy = johnny.get_hitched
>>> billy("Junebug")
'Big Papa + Junebug TLFE'
>>> dill.detect.reference(billy)
4299844816
>>> dill.detect.reference(johnny.get_hitched)
4299844816
>>> dill.detect.reference(johnny)
4299844816
>>> dill.detect.reference(johnny.name)
4332529152
>>> dill.detect.reference(Parent)
4332953328
>>> dill.detect.at(4332529152)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/Users/mikekilmer/Envs/GLITCH/lib/python2.7/site-packages/dill/dill.py", line 738, in _locate_object
    raise ReferenceError("Cannot reference object at '%s'" % address)
ReferenceError: Cannot reference object at '0x1023d2600'
>>> 0x1023d2600
4332529152
>>> id(johnny.name)
4332529152
>>> type(johnny.name)
<type 'str'>
4

2 回答 2

1

Detect.at() takes a reference number and, if it is a reference number that would be handle by the garbage collect module, returns the object that it is associated with. Otherwise returns ReferenceError: and the hex value of the reference number.

For example, instance attributes are not managed by GC because they will be destroyed when the objects they are linked to are destroyed.

As roippi says in comment:

All they're doing here is searching through gc.get_objects() and comparing objects by id - which is exactly how you're supposed to use id. The actual reason you can't dereference johnny.name is that class/instance attributes are not directly tracked by the garbage collector - there's no need to, since you can just destroy them when you destroy the objects they're linked to.

And the hex number is simply the result of calling the hex() method on the reference number input to dill.detect.at().

于 2014-09-15T22:52:48.010 回答
0

这里的基本问题:对象的 id() 不是它的地址。它可能碰巧在 CPython 中,但它不是你可以使用的东西。我不知道 _locate_object 应该用于什么,但这看起来像根本上糟糕的代码。你能解释一下你在这里真正想要完成的事情吗?

Python 不适用于内存地址,它适用于对象引用。每个对象都有一个标识,它是一个整数。一些 Python 在请求 id() 时只是简单地分配顺序整数,仅此而已。您可以确定的是,没有两个同时存在的不同对象具有相同的 id,并且对象的 id 在其整个生命周期中永远不会改变。

于 2014-09-13T05:11:24.817 回答