|
Как создать массив с особым прототипом?
Нужно создать массив со своим кастомным прототипом.
Если в браузере доступно свойство __proto__, то можно сделать так:
function MyArray () {
var instance = []
instance.__proto__ = arguments.callee.prototype
return instance
}
MyArray.prototype.myFunction = function () {}
var myArray = new MyArray()
alert( typeof myArray.myFunction )
А как сделать такое же без __proto__ ? |
Мб так:
function MyArray () {}
MyArray.prototype = Array.prototype;
MyArray.prototype.myFunction = function () {
return this[0] + this[1]
}
var myArray = new MyArray()
alert([
typeof myArray.myFunction,
myArray instanceof Array,
typeof myArray
])
myArray.push(5)
myArray.push(3)
alert([
myArray.length,
myArray.myFunction()
])
...но зачем? |
Aetae
function MyArray () {}
MyArray.prototype = Array.prototype;
MyArray.prototype.myFunction = function () {
return this[0] + this[1]
}
var myArray = new MyArray()
// во-первых мы изменили прототип Array, но это решаемо
alert( typeof [].myFunction )
// во-вторых, мы получили таки объект, а не массив
alert( Array.isArray(myArray) )
alert( Object.prototype.toString.call(myArray) )
А должно быть так:
function MyArray () {
var instance = []
instance.__proto__ = arguments.callee.prototype
return instance
}
MyArray.prototype.myFunction = function () {}
var myArray = new MyArray()
alert( typeof [].myFunction )
alert( Array.isArray(myArray) )
alert( Object.prototype.toString.call(myArray) )
Зачем это? Пытаюсь заставить библиотеку Zepto работать с IE. А там как раз использется массив, а не объект. Да и вообще интересно - возможно ли так сделать без __proto__ |
var MyArray = function() {
var _myPrototype = {
joinReverse : function(s) { return this.slice(0).reverse().join(s); }
}
return function() {
var ret = Array.apply( null, arguments );
for( var i in _myPrototype )
// if( typeof _myPrototype[i] == "function" )
ret[i] = _myPrototype[i];
return ret;
}
}();
var test = MyArray( 1, "bb", 333 );
alert( test.joinReverse( " - " ) );
|
Цитата:
Цитата:
Цитата:
Ну или вручную навешивать на каждый создаваемый массив методы, что, естесно, скажется на производительности и будет вылезать в for in. ...upd: пока писал - последний вариант реализовал rgl.) |
function MEGAArray (){};
MEGAArray.prototype = new Array;
MEGAArray.prototype.godOfJavascript = function(){};
Прототипное наследование не, не слышали? |
Цитата:
function MEGAArray (){};
MEGAArray.prototype = new Array;
var test = new MEGAArray();
test[0] = "a";
test[1] = "bb";
test[2] = "ccc";
alert( test.length );
|
Цитата:
|
rgl, твой вариант некудышный, ибо методов много, а конструктор вызывается часто. Так что думаю потребление ресурсов возрастет ощутимо. Кроме того, прототипа то и нет получается ). А нужно чтобы был прототип. И добавляя метод в прототип мы автоматом получаем его у уже созданных экземпляров.
megaupload, этот вариант я пробовал. В консоли объект действительно выглядит как [массив], вот только Array.isArray не обманешь. Ну и toString также выдает [object Object] А то, что length не обновляется - это не беда. Работа с коллекцией всеравно идет через методы, а не напрямую. Цитата:
В девятке и уж тем более в десятке есть все, что нужно. Так что отсутствие поддержки IE9-10 - это всего лишь наследие zepto. А корень проблемы в использовании __proto__ . Кстати, кто-то говорил что это свойство добавили в стандарт, это так? Если заглянуть сюда https://github.com/madrobby/zepto/issues/ то видно, что не я один хочу поддержки IE. Цитата:
|
function MyArray() {}
MyArray.prototype = [];
MyArray.prototype.toString = function(){alert('ну вы нубы')};
var q = new MyArray();
q.push(1);
q.push(1);
alert(q.length);
q+"";
|
| Часовой пояс GMT +3, время: 06:10. |
|