24.10.2014, 21:33
|
Аспирант
|
|
Регистрация: 15.02.2013
Сообщений: 55
|
|
Виртуальный класс а-ля Си Плас Плас
Здравствуйте хочу реализовать сабж в JS.
Есть вот такой код:
function Interface() {};
Interface.prototype.p1 = "property1";
function Class() {};
Class.prototype = new Interface();
var obj = new Class();
console.log(obj.p1);
Так всё работает как надо, но у меня есть один вопрос. Почему в свойстве prototype "класса наследника" Class нужно указывать именно экземпляр функции-конструктора Interface, а не саму функцию-конструктор. А то получается, что нужно сначала потратить память для создания объекта, а потом уже только я получаю возможность "наследования". А если я буду наследовать 20 "классов"?
#1 В принципе, можно использовать один созданный объект для этих 20 "классов", но мне всё равно хочется узнать, как можно обойтись без создания экземпляра родительской функции-конструктора..
Последний раз редактировалось Voronar, 24.10.2014 в 21:38.
|
|
24.10.2014, 22:32
|
Кандидат Javascript-наук
|
|
Регистрация: 14.10.2014
Сообщений: 117
|
|
Сообщение от Voronar
|
А то получается, что нужно сначала потратить память для создания объекта, а потом уже только я получаю возможность "наследования".
|
Короче, за пвмять особо не беспокойся. Так как на твой объект никто не ссылается, его загребет GC, но если это тебя беспокоит, можешь сделать вот так
function Interface() {};
Interface.prototype.p1 = "property1";
function Class() {};
Class.prototype = Interface.prototype
var obj = new Class();
alert(obj.p1);
Толко это не прокатит, если ты хочешь сделать Class реально наследником Interface, а не только наследовать от его прототипа. Но в твоем случае и так сойдет. То что ты написал, имеет смысл, только если
function Interface() {this.a=1; this.b=2};
Interface.prototype.p1 = "property1";
function Class() {};
Class.prototype = new Interface
var obj = new Class();
alert([obj.p1, obj.a, obj.b]);
Последний раз редактировалось terminator-101, 24.10.2014 в 22:40.
|
|
24.10.2014, 22:40
|
Аспирант
|
|
Регистрация: 15.02.2013
Сообщений: 55
|
|
Да, я буду расширять, обязательно.
Так как ты указал я делал. Проблема возникает, когда я хочу сделать вот так:
Class.prototype.p1 = "new value";
В этом случае свойство меняется у базового класса Interface, а мне нужно поменять прототип c одноимённым свойством только для Class.
|
|
24.10.2014, 22:46
|
Кандидат Javascript-наук
|
|
Регистрация: 14.10.2014
Сообщений: 117
|
|
Сообщение от Voronar
|
В этом случае свойство меняется у базового класса Interface, а мне нужно поменять прототип c одноимённым свойством только для Class.
|
Ну так указывай тогда этот прототип только для Class, нахрен ты на Interface его вешаешь?
|
|
24.10.2014, 22:58
|
Кандидат Javascript-наук
|
|
Регистрация: 14.10.2014
Сообщений: 117
|
|
Voronar,
Короче, Class не обязан наследовать прототип Interface, он может иметь и свой собственный прототип. Тогда его экземпляры будут лазить за этим свойством именно в прототип родителя. А вообще, непонятны твои цели, что именно ты хочешь реализовать. Может в твоей задаче вообще классы не нужны. В JS Можно наследовать и напрямую от объектов. В любом случае, реализовать можно любую модель, как 2 пальца об асфальт.
|
|
24.10.2014, 23:03
|
Аспирант
|
|
Регистрация: 15.02.2013
Сообщений: 55
|
|
В "классе" Interface я хочу сделать чистые виртуальные функции, то есть аналог С++ ООП-интерфейса.
Когда я буду реализовывать эти функции в Class1, Class2 и Classn, то функции прототипа Interface будут каждый раз перетираться. А я хочу иметь реализации функций из Interface для каждого экземпляра Class1, Class2 и Classn, и чтобы у меня имелось только одно объявления функции для каждого класса.
Можно описать эти классы по отдельности, но я хочу их наследовать от базового виртуального класса Interface.
|
|
24.10.2014, 23:13
|
Аспирант
|
|
Регистрация: 15.02.2013
Сообщений: 55
|
|
function Interface() {};
Interface.prototype.fd = "file descriptor";
Interface.prototype.open = "virtual function";
Interface.prototype.close = "virtual function";
function Class1() {};
function Class2() {};
Class1.prototype = new Interface();
Class2.prototype = new Interface();
Class1.prototype.open = function()
{
alert("open1");
};
Class1.prototype.close = function()
{
alert("close1");
};
Class2.prototype.open = function()
{
alert("open2");
};
Class2.prototype.close = function()
{
alert("close2");
};
var obj1 = new Class1();
var obj2 = new Class2();
obj1.open();
obj2.open();
Работает так, как я хочу, но в итоге мне нужно создавать для каждого наследника новый экземпляр Interface, а я хочу обойтись минимальными затратами памяти.
Последний раз редактировалось Voronar, 24.10.2014 в 23:45.
|
|
24.10.2014, 23:19
|
Кандидат Javascript-наук
|
|
Регистрация: 14.10.2014
Сообщений: 117
|
|
Сообщение от Voronar
|
В "классе" Interface я хочу сделать чистые виртуальные функции, то есть аналог С++ ООП-интерфейса.
Когда я буду реализовывать эти функции в Class1, Class2 и Classn, то функции прототипа Interface будут каждый раз перетираться. А я хочу иметь реализации функций из Interface для каждого экземпляра Class1, Class2 и Classn, и чтобы у меня имелось только одно объявления функции для каждого класса.
Можно описать эти классы по отдельности, но я хочу их наследовать от базового виртуального класса Interface.
|
Не знаю, что там в ++, но похоже на это.
function Interface() {};
Interface.prototype.p1 = "property1";
function Class(prop) {if(prop) this.p1=prop};
Class.prototype = new Interface
o1=new Class();
o2=new Class("foo")
alert([o1.p1, o2.p1]);
Последний раз редактировалось terminator-101, 24.10.2014 в 23:21.
|
|
24.10.2014, 23:31
|
Аспирант
|
|
Регистрация: 15.02.2013
Сообщений: 55
|
|
Сообщение от terminator-101
|
Не знаю, что там в ++, но похоже на это.
function Interface() {};
Interface.prototype.p1 = "property1";
function Class(prop) {if(prop) this.p1=prop};
Class.prototype = new Interface
o1=new Class();
o2=new Class("foo")
alert([o1.p1, o2.p1]);
|
Может я ошибаюсь, но мне кажется, что в этом случае функция(объект), имя которой ты передаёшь как параметр конструктора, будет создаваться для каждого экземпляра (так как ты используешь this), а это слишком затратно.
Я описал своё видение в примере, приведённом мной выше.
Из моего примера видно, что для любого экземпляра Class1 или Class2, этот экземпляр будет иметь только одну реализацию функции в прототипе. То есть получается, что по-любому для каждого наследника нужно создавать экземпляр Interface.
|
|
25.10.2014, 03:23
|
Профессор
|
|
Регистрация: 23.10.2010
Сообщений: 2,718
|
|
Сообщение от Voronar
|
А если я буду наследовать 20 "классов"?
|
Кавычки поставили позже, на 2 слова раньше надо.
Что вы задумали то не имеет смысла. Пишите на этом языке, а не на том, который вы лучше знаете. В штатах люди живут годами после переезда и не говорят по-английски, так и вы собираетесь писать на js как в тылу врага.
|
|
|
|