Почему не получается удалить атрибут экземпляра класса, унаследованный от родителя, но в самом классе его удалить можно?

class Point3D:
    x = 7
    y = 5
    z = 5


e = Point3D()
print(e.z)
delattr(e, 'z')

Ответы (3 шт):

Автор решения: sopython
class Point3D:
    x = 7
    y = 6
    z = 5


e = Point3D()
print(e.z)

print(hasattr(e, 'z')) # До удаления
delattr(Point3D, 'z')
print(hasattr(e, 'z')) # После удаления
→ Ссылка
Автор решения: MarianD

Вы определили z как атрибут класса, потому его невозможно удалить ссылкой на объект этого класса.

Для определения z как атрибута объекта этого класса, возможно применить разные подходы:

  1. Определить аттрибут в классе, но как атрибут им созданных объектов, с начальным значением:

    class Point3D:
        x = 7
        y = 5
        def __init__(self):
            self.z = 5
    

    В этом случае ваше последующие команды не нужно изменить.


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

    class Point3D:
        x = 7
        y = 5
        def __init__(self, z=5):
            self.z = z
    

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

      e = Point3D(127)       # или e = Point3D(z=127)
    

  1. Совсем не определить z в классе:

     class Point3D:
         x = 7
         y = 5
    

    а определить его только после создания объекта:

     e = Point3D
     e.z = 5             # создание аттрибута z только для объекта е
    


Примечание:

Лучше всего определить и переменные x и y как переменные объектов этого класса, например так:

class Point3D:
   def __init__(self, x=0, y=0, z=0):
       self.x = x
       self.y = y
       self.z = z
→ Ссылка
Автор решения: Xander

Во-первых, в приведённом вами коде нет ни наследования, ни какого-либо родителя. Вероятно, вы имели в виду не "наследование", а "инстанцирование экземпляра"? Это два совершенно разных понятия.

Что касается вашего вопроса: дело в том, что в вашем случае экземпляр не обладает собственным аттрибутом "z". Он может обращаться к соответствующему аттрибуту класса, но сам его не имеет. Поэтому и удалять его нельзя.

→ Ссылка