поясните плиз глубокий смысл
От: Oleg A. Bachin Украина  
Дата: 24.08.11 21:57
Оценка:
добрый всем!

вобщем решил покопаться что тут новенького (для меня) и обнаружил такие конструкции:
class constructor, class var ну и т.п... попробовал разобраться, но...
  ta = class
    class var fc1: integer;
    class constructor create();
  end;

  tb = class(ta)
  end;

1. ну во-первых для меня не понятно, почему после наследования, конструктор вызывается только у базового класса.
2. вызывается он явно во время инициализации модуля. таким образом не пойму чем он отличается от секции initialization
3. вобщем то этот пункт и есть причина, которая меня окончательно поставила в тупик. @ta.fc1 = @tb.fc1. это что вообще такое? новый способ написания багов?
Best regards,
Oleg A. Bachin
Re: поясните плиз глубокий смысл
От: hattab  
Дата: 25.08.11 06:17
Оценка:
Здравствуйте, Oleg A. Bachin, Вы писали:

OAB> 1. ну во-первых для меня не понятно, почему после наследования, конструктор вызывается только у базового класса.


Он вызывается только в том классе, в котором определен. Потому что:

Normally, class constructors are used to initialize the static fields of the class or to perform a type of initialization, which is required before the class or any class instance can function properly.


OAB> 2. вызывается он явно во время инициализации модуля. таким образом не пойму чем он отличается от секции initialization


Even though the same result can be obtained by placing class initialization code into the initialization section, class constructors have the benefit of helping the compiler decide which classes should be included into the final binary file and which should be removed from it.


OAB> 3. вобщем то этот пункт и есть причина, которая меня окончательно поставила в тупик. @ta.fc1 = @tb.fc1. это что вообще такое? новый способ написания багов?


Это работа механизма наследования. Оно так для любой "class" сущности В чем конкретно проблема?
avalon 1.0rc3 rev 419, zlib 1.2.3
Re[2]: поясните плиз глубокий смысл
От: Oleg A. Bachin Украина  
Дата: 25.08.11 21:00
Оценка:
Здравствуйте, hattab, Вы писали:

OAB>> 3. вобщем то этот пункт и есть причина, которая меня окончательно поставила в тупик. @ta.fc1 = @tb.fc1. это что вообще такое? новый способ написания багов?


H>Это работа механизма наследования. Оно так для любой "class" сущности В чем конкретно проблема?


да ну? класс — это такой же объект, только мета. два класса — значит должно быть два мета объекта. и впринципе их два, но почему-то class var для них глобальный. по сути это не переменная класса, а глобальная переменная.
так же как и на каждый класс создается свой vmt, где-то рядом должны быть и переменные класса.
Best regards,
Oleg A. Bachin
Re[3]: поясните плиз глубокий смысл
От: hattab  
Дата: 25.08.11 21:58
Оценка:
Здравствуйте, Oleg A. Bachin, Вы писали:

OAB> OAB>> 3. вобщем то этот пункт и есть причина, которая меня окончательно поставила в тупик. @ta.fc1 = @tb.fc1. это что вообще такое? новый способ написания багов?


OAB> H>Это работа механизма наследования. Оно так для любой "class" сущности В чем конкретно проблема?


OAB> да ну? класс — это такой же объект, только мета.


Мета в дельфях ни что иное, как обычная ссылка.

OAB> два класса — значит должно быть два мета объекта. и впринципе их два, но почему-то class var для них глобальный. по сути это не переменная класса, а глобальная переменная.

OAB> так же как и на каждый класс создается свой vmt, где-то рядом должны быть и переменные класса.

Так ты проверь еще и адреса методов класса, судя по всему, удивишься. Новыми сущностями для потомков они станут, в случае методов, после их виртуализации с последующим перекрытием, в случае переменных после их редекларации. А так ты верно говоришь, переменные класса суть глобальные переменные ограниченные областью видимости класса и их потомков (с учетом модификаторов видимости)
avalon 1.0rc3 rev 419, zlib 1.2.3
Re[4]: поясните плиз глубокий смысл
От: Oleg A. Bachin Украина  
Дата: 26.08.11 08:53
Оценка:
Здравствуйте, hattab, Вы писали:

с трудом допускаю мысль, что все же ты прав, но пока у меня в голове это не укладывается...

H>Так ты проверь еще и адреса методов класса, судя по всему, удивишься. Новыми сущностями для потомков они станут, в случае методов, после их виртуализации с последующим перекрытием, в случае переменных после их редекларации.

все верно, адреса — это данные, у нас же речь идет о памяти под эти данные. а вот адреса для ta и tb у нас разные.
попробую объяснить как я себе представляю переменную класса.
возьмем к примеру vmtMethodTable. относительно адреса класса у нас расположена табличка методов класса, а в ней уже ссылка на метод. да, если метод не перекрыт, то в табличке будет один и тот же адрес, но изначально адрес где хранится ссылка на метод другой. вобщем то и предсталял себе примерно такую схему...

H>А так ты верно говоришь, переменные класса суть глобальные переменные ограниченные областью видимости класса и их потомков (с учетом модификаторов видимости)

вот в том то и дело. глобальные переменные у нас и так есть, а переменных класса нет. зачем вводить было новую конструкцию языка, не добавляя функционал?
Best regards,
Oleg A. Bachin
Re[5]: поясните плиз глубокий смысл
От: hattab  
Дата: 26.08.11 10:21
Оценка:
Здравствуйте, Oleg A. Bachin, Вы писали:

OAB> H>Так ты проверь еще и адреса методов класса, судя по всему, удивишься. Новыми сущностями для потомков они станут, в случае методов, после их виртуализации с последующим перекрытием, в случае переменных после их редекларации.


OAB> все верно, адреса — это данные, у нас же речь идет о памяти под эти данные. а вот адреса для ta и tb у нас разные.


Ну да, это же (ta и tb) разные сущности, в то время, как метод класса в потомке есть сущность наследованная и станет новой только после перекрытия/переопределения. Точно так же и с переменными класса

OAB> вот в том то и дело. глобальные переменные у нас и так есть, а переменных класса нет. зачем вводить было новую конструкцию языка, не добавляя функционал?


Теперь вот (не то с 2005, не то с 2006) у нас есть и переменные класса. Что в свою очередь позволяет избежать конфликта имен т.к. для доступа к ним нужно использовать fully qualified name. Да и просто улучшает инкапсуляцию.
avalon 1.0rc3 rev 419, zlib 1.2.3
Re[6]: поясните плиз глубокий смысл
От: Oleg A. Bachin Украина  
Дата: 27.08.11 08:09
Оценка:
Здравствуйте, hattab, Вы писали:

....
давай попробуем по-другому...
class = record
  ...
  vmtClassVarTable: pArrayOfVars;
  ...
end
ta: class;
tb: class = ta;

да, пока не перекроем, ЗНАЧЕНИЕ tb.vmtClassVarTable[0] будет то же что и у ta. но адрес изначально другой.

ЗЫ фиг с ним, по сути думаю ноги растут от class constructor. ведь если он вызывается только у базового класса, будем иметь проблемы с инициализацией в случае если переменная класса будет создаваться на класс...
Best regards,
Oleg A. Bachin
Re[7]: поясните плиз глубокий смысл
От: hattab  
Дата: 27.08.11 09:33
Оценка:
Здравствуйте, Oleg A. Bachin, Вы писали:

OAB> ....

OAB> давай попробуем по-другому...
OAB>
class = record
OAB>   ...
OAB>   vmtClassVarTable: pArrayOfVars;
OAB>   ...
OAB> end
OAB> ta: class;
OAB> tb: class = ta;

OAB> да, пока не перекроем, ЗНАЧЕНИЕ tb.vmtClassVarTable[0] будет то же что и у ta. но адрес изначально другой.

Ну так адрес другой оно и понятно, ведь ta и tb разные сущности. В то время, как сущности объявленные "классовыми" наследуются потомками. Я в упор не вижу противоречий

OAB> ЗЫ фиг с ним, по сути думаю ноги растут от class constructor. ведь если он вызывается только у базового класса, будем иметь проблемы с инициализацией в случае если переменная класса будет создаваться на класс...


По моему, достаточно просто понимать, что обычной переменной (полем) владеет конкретный объект, в то время, как переменной класса владеет класс и потомки.
avalon 1.0rc3 rev 419, zlib 1.2.3
Re[8]: поясните плиз глубокий смысл
От: Oleg A. Bachin Украина  
Дата: 27.08.11 20:32
Оценка:
Здравствуйте, hattab, Вы писали:

H>По моему, достаточно просто понимать, что обычной переменной (полем) владеет конкретный объект, в то время, как переменной класса владеет класс и потомки.


ну вот я и не понимаю, почему это называется переменной класса! ведь если проводить вашу же паралель, то в первом случае (с объектом) для каждого объекта будет своя переменная, а во втором случае одна переменная для всех классов. по сути глобальная. уже б так и писали бы:
var
  global_var: integer;

type
  ta = class
    class property fictive_class_var: integer read global_var write global_var;
  end;
Best regards,
Oleg A. Bachin
Re[9]: поясните плиз глубокий смысл
От: hattab  
Дата: 27.08.11 21:50
Оценка:
Здравствуйте, Oleg A. Bachin, Вы писали:

OAB> H>По моему, достаточно просто понимать, что обычной переменной (полем) владеет конкретный объект, в то время, как переменной класса владеет класс и потомки.


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


Поля объекта отражают состояние только конкретного объекта, в то время, как переменные класса отражает состояние класса вцелом. Причем говоря о классе, мы не может не подразумевать и его потомков т.к. даже самый нижний потомок является представителем верхнего класса-предка. Я к тому веду, что изменив поле объекта мы изменяем лишь сам объект, а изменив переменную класса мы мы оказываем влияние на класс вцелом.

Пример из жизни. Есть класс, объекты которого могут иметь весьма и весьма большое внутреннее состояние (от байтов, до нескольких гигабайт). Память не резиновая, поэтому в базовом классе предусмотрен механизм ограничения использования памяти. Класс имеет свойство класса (через переменную класса разумеется) TotalMemoryLimit и свойство MemoryLimit. Свойство MemoryLimit указывает, какое количество памяти может использовать объект для хранения своего внутреннего состояния. Свойство TotalMemoryLimit указывает какое количество памяти может быть использовано всеми объектами данного класса и его потомков. Весь функционал контроля лимитов выполнен в базовом классе, потому потомки этого класса реализуют только процесс переноса состояния из памяти в некое новое хранилище (файл, БД и т.п.) и обеспечивают последующий прозрачный доступ к нему. То есть, имея в базовом классе свойство TotalMemoryLimit, в виде переменной класса, мы можем управлять лимитом для всех его потомков. В случае, когда переменная была бы индивидуальной для каждого класса потомка, задача изменения лимита была бы крайне затруднительной (если не сказать невозможной), и профита от задействования полиморфизма (классы потомки реализующие различные хранилища) мы бы не получили.

OAB> по сути глобальная. уже б так и писали бы:

OAB>
OAB> var
OAB>   global_var: integer;

OAB> type
OAB>   ta = class
OAB>     class property fictive_class_var: integer read global_var write global_var;
OAB>   end;
OAB>


Прямое нарушение инкапсуляции
avalon 1.0rc3 rev 419, zlib 1.2.3
Re[10]: поясните плиз глубокий смысл
От: Oleg A. Bachin Украина  
Дата: 28.08.11 07:32
Оценка:
все, вопрос снимаю. полез глянуть как с этим делом в других языках — не только у меня такие вопросы возникают.
для джавы и раби нашел даже workaround.
вот о чем я говорю:
http://moonmaster9000.tumblr.com/post/477872071/class-variables-and-inheritance-in-ruby
Best regards,
Oleg A. Bachin
Re[11]: поясните плиз глубокий смысл
От: de Niro Ниоткуда  
Дата: 30.08.11 06:10
Оценка:
Здравствуйте, Oleg A. Bachin, Вы писали:

OAB>для джавы и раби нашел даже workaround.


ruby произносится как "рУби"
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.