23.03.2014, 17:14
|
|
|
Регистрация: 10.07.2008
Сообщений: 3,873
|
|
Array.prototype.copyWithin
|
|
23.03.2014, 18:49
|
Особый гость
|
|
Регистрация: 02.04.2010
Сообщений: 4,260
|
|
Хм.
describe('Array#copyWithin', function() {
it('has the right arity', function() {
expect(Array.prototype.copyWithin.length).to.equal(2);
});
it('works with 2 args', function() {
expect([1, 2, 3, 4, 5].copyWithin(0, 3)).to.eql([4, 5, 3, 4, 5]);
expect([1, 2, 3, 4, 5].copyWithin(1, 3)).to.eql([1, 4, 5, 4, 5]);
expect([1, 2, 3, 4, 5].copyWithin(1, 2)).to.eql([1, 3, 4, 5, 5]);
expect([1, 2, 3, 4, 5].copyWithin(2, 2)).to.eql([1, 2, 3, 4, 5]);
});
it('works with 3 args', function() {
expect([1, 2, 3, 4, 5].copyWithin(0, 3, 4)).to.eql([4, 2, 3, 4, 5]);
expect([1, 2, 3, 4, 5].copyWithin(1, 3, 4)).to.eql([1, 4, 3, 4, 5]);
expect([1, 2, 3, 4, 5].copyWithin(1, 2, 4)).to.eql([1, 3, 4, 4, 5]);
});
it('works with negative args', function() {
expect([1, 2, 3, 4, 5].copyWithin(0, -2)).to.eql([4, 5, 3, 4, 5]);
expect([1, 2, 3, 4, 5].copyWithin(0, -2, -1)).to.eql([4, 2, 3, 4, 5]);
expect([1, 2, 3, 4, 5].copyWithin(-4, -3, -2)).to.eql([1, 3, 3, 4, 5]);
expect([1, 2, 3, 4, 5].copyWithin(-4, -3, -1)).to.eql([1, 3, 4, 4, 5]);
expect([1, 2, 3, 4, 5].copyWithin(-4, -3)).to.eql([1, 3, 4, 5, 5]);
});
it('works with arraylike objects', function() {
var args = (function () { return arguments; }(1, 2, 3));
expect(Array.isArray(args)).not.to.be.ok;
var argsClass = Object.prototype.toString.call(args);
expect(Array.prototype.slice.call(args)).to.eql([1, 2, 3]);
Array.prototype.copyWithin.call(args, -2, 0);
expect(Array.prototype.slice.call(args)).to.eql([1, 1, 2]);
expect(Object.prototype.toString.call(args)).to.equal(argsClass);
});
});
copyWithin: function(target, start) {
var end = arguments[2]; // copyWithin.length must be 2
var o = ES.ToObject(this);
var len = ES.ToLength(o.length);
target = ES.ToInteger(target);
start = ES.ToInteger(start);
var to = target < 0 ? Math.max(len + target, 0) : Math.min(target, len);
var from = start < 0 ? Math.max(len + start, 0) : Math.min(start, len);
end = (end===undefined) ? len : ES.ToInteger(end);
var fin = end < 0 ? Math.max(len + end, 0) : Math.min(end, len);
var count = Math.min(fin - from, len - to);
var direction = 1;
if (from < to && to < (from + count)) {
direction = -1;
from += count - 1;
to += count - 1;
}
while (count > 0) {
if (_hasOwnProperty.call(o, from)) {
o[to] = o[from];
}
else {
delete o[from];
}
from += direction;
to += direction;
count -= 1;
}
return o;
}
Последний раз редактировалось monolithed, 23.03.2014 в 18:53.
|
|
23.03.2014, 18:56
|
|
|
Регистрация: 10.07.2008
Сообщений: 3,873
|
|
Не ну найти реализацию и посмотреть результаты я в состоянии. Меня интересует зачем кому-то так часто требовались такие преобразования массива, чтобы добавлять метод в спецификацию. Не могу придумать применения.
|
|
23.03.2014, 19:06
|
Особый гость
|
|
Регистрация: 02.04.2010
Сообщений: 4,260
|
|
А ты об этом, я тоже в недоумении
|
|
23.03.2014, 19:53
|
|
|
Регистрация: 10.07.2008
Сообщений: 3,873
|
|
Переписал пример реализации выше без лишних проверок в надежде понять нафиг это нужно
if (!Array.prototype.copyWithin) {
Array.prototype.copyWithin = function(target, start, end) {
var length = this.length, count, direction,
to = target < 0 ? Math.max(length + target, 0) : Math.min(target, length),
from = start < 0 ? Math.max(length + start, 0) : Math.min(start, length);
end = typeof end == "undefined" ? length : end;
end = end < 0 ? Math.max(length + end, 0) : Math.min(end, length);
count = Math.min(end - from, length - to);
direction = 1;
if (from < to && to < (from + count)) {
direction = -1;
from += count - 1;
to += count - 1;
}
while (count > 0) {
if (from in this) {
this[to] = this[from];
}
else {
delete this[from];
}
from += direction;
to += direction;
count -= 1;
}
return this;
};
}
alert([
[1, 2, 3, 4, 5].copyWithin(0, 3).toString() == [4, 5, 3, 4, 5].toString(),
[1, 2, 3, 4, 5].copyWithin(1, 3).toString() == [1, 4, 5, 4, 5].toString(),
[1, 2, 3, 4, 5].copyWithin(1, 2).toString() == [1, 3, 4, 5, 5].toString(),
[1, 2, 3, 4, 5].copyWithin(2, 2).toString() == [1, 2, 3, 4, 5].toString(),
[1, 2, 3, 4, 5].copyWithin(0, 3, 4).toString() == [4, 2, 3, 4, 5].toString(),
[1, 2, 3, 4, 5].copyWithin(1, 3, 4).toString() == [1, 4, 3, 4, 5].toString(),
[1, 2, 3, 4, 5].copyWithin(1, 2, 4).toString() == [1, 3, 4, 4, 5].toString(),
[1, 2, 3, 4, 5].copyWithin(0, -2).toString() == [4, 5, 3, 4, 5].toString(),
[1, 2, 3, 4, 5].copyWithin(0, -2, -1).toString() == [4, 2, 3, 4, 5].toString(),
[1, 2, 3, 4, 5].copyWithin(-4, -3, -2).toString() == [1, 3, 3, 4, 5].toString(),
[1, 2, 3, 4, 5].copyWithin(-4, -3, -1).toString() == [1, 3, 4, 4, 5].toString(),
[1, 2, 3, 4, 5].copyWithin(-4, -3).toString() == [1, 3, 4, 5, 5].toString(),
].every(function (testResult) {
return testResult;
}));
|
|
23.03.2014, 20:12
|
Особый гость
|
|
Регистрация: 02.04.2010
Сообщений: 4,260
|
|
Сообщение от Octane
|
в надежде понять нафиг это нужно
|
Если ты понял расскажи, а я тоже не вкурю зачем это нужно в стандарте
|
|
23.03.2014, 21:21
|
|
|
Регистрация: 10.07.2008
Сообщений: 3,873
|
|
думаю базовые 2 случая copyWithin(0, 1) и copyWithin(1, 0), а остальное потом накрутили
[1, 2, 3, 4, 5].copyWithin(0, 1)
↓
[2, 3, 4, 5, 5].copyWithin(0, 1)
↓
[3, 4, 5, 5, 5].copyWithin(0, 1)
↓
[4, 5, 5, 5, 5].copyWithin(0, 1)
↓
[5, 5, 5, 5, 5].copyWithin(0, 1)
[1, 2, 3, 4, 5].copyWithin(1, 0)
↓
[1, 1, 2, 3, 4].copyWithin(1, 0)
↓
[1, 1, 1, 2, 3].copyWithin(1, 0)
↓
[1, 1, 1, 1, 2].copyWithin(1, 0)
↓
[1, 1, 1, 1, 1].copyWithin(1, 0)
похоже на shift и unshift без изменения длины
|
|
24.03.2014, 00:45
|
Особый гость
|
|
Регистрация: 02.04.2010
Сообщений: 4,260
|
|
С трудом могу представить практическую ценность данного метода.
|
|
25.03.2014, 00:04
|
|
junior
|
|
Регистрация: 29.11.2011
Сообщений: 3,924
|
|
Сообщение от Octane
|
Не пойму, для чего нужен метод copyWithin
|
кто-то по блату пролоббировал
__________________
Чебурашка стал символом олимпийских игр. А чего достиг ты?
Тишина - самый громкий звук
|
|
|
|