Итак, у меня есть этот класс

class table:
    h = 0
    g = 0

И у меня есть один элемент этого класса под названием aux.

aux = table

Aux.g равен нулю.
Позже я вызываю эту функцию move (aux)

move(x):
    newTable = table
    newTable.g = x.g + 1

NewTable.g получает 1, как и ожидалось, но x.g также меняется с 0 на 1. Почему?
Заранее спасибо, Адриано

0
Adriano Ferrari Cardoso 16 Дек 2015 в 23:57

4 ответа

Лучший ответ

Это потому, что вы объявляете эквивалент переменной статического класса и когда вы обновляете это, он обновляется для каждого экземпляра этого класса. Вам нужно объявить переменные экземпляра следующим образом:

class table:
    def __init__(self):
        self.h = 0
        self.g = 0

Теперь, когда вы создаете экземпляр класса следующим образом: aux = table(), он присваивает значения этому экземпляру таблицы - просто переменной aux.

Ваша функция перемещения будет выглядеть так:

move(x):
    newTable = table()
    newTable.g = x.g + 1

Который будет увеличивать значение newTable.g, но не значение x.g. Возможно, вы также захотите вернуть новую таблицу следующим образом: return newTable, и затем вы сможете использовать ее в других функциях.

Стоит отметить, что в вашем коде вы никогда не выполняете создание экземпляров класса таблицы. Это означает, что когда вы присваиваете aux = table, он просто присваивает ссылку на класс вашей переменной aux. Чтобы создать экземпляр класса, вы вызываете класс, как если бы вы были функцией - это называется конструктором - и он вызывает метод __init__ класса. Поэтому, когда я объявляю aux = table(), выполняется метод table __init__, а затем возвращается новый экземпляр класса.

6
Community 23 Май 2017 в 11:45

Определяя атрибуты только для класса, они привязываются ко всему классу (статическому), а не к отдельным экземплярам (или объектам). То, что вы скорее хотите, это назначить их внутри конструктора:

class Table:
    def __init__(self):
        self.h = 0
        self.g = 0

    def move(self, delta):
        self.h += deta

Обратите внимание, что я также изменил функцию перемещения на метод. Разница в том, что метод изменяет состояние отдельных экземпляров.

Затем вы можете создавать экземпляры и работать с ними так:

t1 = Table()
t2 = Table()
t1.move(10)
print(t1.h)   # will print 10
print(t2.h)   # will print 0
2
Hubert Grzeskowiak 23 Дек 2015 в 03:53

h и g являются статическими, то есть «переменными класса». h и g не являются уникальными для объекта класса table, но являются атрибутами самого этого класса.

2
timgeb 16 Дек 2015 в 21:06

Когда вы сделали это:

aux = table

И это:

newTable = table

Вы не создали новые экземпляры объектов класса table. Вы просто ссылаетесь на собственный экземпляр класса table с двумя разными переменными. Короче говоря, aux и newTable ссылка (простите меня за это; укажите на ) одно и то же.

Обратите внимание, что h, g являются общими атрибутами класса table. Они являются общими для всех экземпляров класса table.

2
Quirk 16 Дек 2015 в 21:14