Owerwriting de los resultados de la clase en datos antiguos en Python

Recently run into following problem using python 2.7: I have class like this:

class Comment():
    def __init__(self, preComments = [], postComment = ''):
        self.__preComments = preComments
        self.__postComment = postComment

I use code like this multiple times:

# self.commentQueue holds comment.Comment()
def getQueuedComment(self):
    queuedComment = self.commentQueue
    self.commentQueue = comment.Comment()
    return queuedComment

Idea of this code is to return instance of Comment and create new instance in place, so queuing may continue.

And result is that weirdly, but each time second code is called self.commentQueue holds data from all other instances of this class(data are appended not assigned and problem occurs only with list), but as I understand that self.commentQueue = comment.Comment() should create new, empty class, by empty I mean that self.__preComments = [] y self.__postComment = ''.

Fix is to call self.commentQueue = comment.Comment([], '') en lugar de self.commentQueue = comment.Comment(), but I just don't understand why this happens.

preguntado el 09 de marzo de 12 a las 13:03

2 Respuestas

Nunca usar [] as a default argument value. This expression is only evaluated once, so todos calls to your function will always use the same list instance. Make it like this instead:

class Comment():
    def __init__(self, preComments = None, postComment = None):
        if preComments is not None:
            self.__preComments = preComments
        else:
            self.__preComments = []
        if postComments is not None:
            self.__postComment = postComment
        else:
            self.__postComment = []

respondido 09 mar '12, 13:03

self.__preComments = preComments or [] or something more explicit self.__preComments = [] if preComments is None else preComments - rplnt

Usando año or isn't foolproof, as you cannot pass in a Falsy value. - casey kuball

@Darthfett Yes, that's why I wrote the second example as well. But if we expect it to be a list then it's ok to use or. Luckily, list in python with whatever in it is considered "True". - rplnt

@rpInt Explicit is better than implicit. Just thought I would leave a comment for those who might not know. (Note the fact that I didn't address you in my comment. :) ) - casey kuball

Problem is you use mutable variable type as constructor parameter (preComments = []). See this: "El menor asombro" y el argumento predeterminado mutable

contestado el 23 de mayo de 17 a las 12:05

No es la respuesta que estás buscando? Examinar otras preguntas etiquetadas or haz tu propia pregunta.