Self-referencing lists

前端 未结 3 1973
刺人心
刺人心 2020-12-11 23:39

Say you do the following:

a = [1]
a[0] = a

You end up with a as equal to [[...]]. What\'s going on here? How doe

3条回答
  •  余生分开走
    2020-12-12 00:22

    You ain't seen nothing:

    >>> a = []
    >>> a[:] = [a] * 4
    >>> a
    [[...], [...], [...], [...]]
    

    If you're interested in how this works in CPython, see list_repr in listobject.c and similar functions. Basically, any function that potentially prints a self-referential object calls Py_ReprEnter on the object before printing it and Py_ReprLeave when it is done. (See object.c for the definitions of these functions.) The former checks to see if the object is found in a thread-local stack of objects that are currently being printed (and if not, pushes it); the latter pops the object from the stack. So if Python is printing a list and discovers that the list is on the stack, that must mean that this is a self-referential list, and the list should be abbreviated, to avoid an infinite loop:

     i = Py_ReprEnter((PyObject*)v);
     if (i != 0) {
         return i > 0 ? PyString_FromString("[...]") : NULL;
     }
    
     // ...
    
     Py_ReprLeave((PyObject *)v);
     return result;
    

提交回复
热议问题