Классы Python - изменчивость - PullRequest
1 голос
/ 31 августа 2009

У меня проблема с питоном. У меня тип узла бинарного дерева:

class NODE:
        element = 0
        leftchild = None
        rightchild = None

И мне пришлось реализовать функцию deletemin:

def DELETEMIN( A ):
        if A.leftchild == None:
                retval = A.element
                A = A.rightchild
                return retval
        else:
                return DELETEMIN( A.leftchild )

Тем не менее, когда я пытаюсь проверить это на двоичном дереве:

  1
 / \
0   2

Он должен удалить 0, просто установив его на ноль, но вместо этого я получаю это:

  0
 / \
0   2

Почему я не могу аннулировать узел внутри функции в python? Это способ сделать это?

Ответы [ 2 ]

2 голосов
/ 31 августа 2009

Python передает аргументы по ссылке на объект, точно так же как java, а не по ссылке на переменную. Когда вы присваиваете локальной переменной (включая аргумент) новое значение, вы изменяете только локальную переменную, ничего больше (не путайте это с вызовом мутаторов или присваиванием ATTRIBUTES объектов: мы говорим о присваиваниях на голые имена).

Предпочтительным решением в Python, как правило, является возвращение нескольких значений, сколько вам нужно, и назначение их соответствующим образом в вызывающей программе. Таким образом, deletemin будет возвращать два значения: текущий returnval и измененный узел, и вызывающая сторона назначит последнее по мере необходимости. I.e.:

def DELETEMIN( A ):
        if A.leftchild is None:
                return A.element, A.rightchild
        else:
                return DELETEMIN( A.leftchild )

и в вызывающем абоненте, где у вас ранее было foo = DELETEMIN( bar ), вы использовали бы вместо

foo, bar = DELETEMIN( bar )

Странная заглавная буква и пробел в скобках, кстати, но это другая проблема; -).

Нет способа получить «указатель или ссылку на голое имя вызывающего» (в Python или Java) так, как вы могли бы, например, в C или C ++. Существуют и другие альтернативные подходы, но они требуют других схем, чем вы предпочитаете, поэтому я рекомендую подход с несколькими возвращаемыми значениями, как указано здесь.

0 голосов
/ 31 августа 2009
class Node:
    element = 0;
    left_child = None
    right_child = None

def delete_min( A ):
    if A.left_child is None:
        return A.right_child
    else:
        A.left_child = delete_min(A.left_child)
        return A

tree = delete_min(tree)
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...