array prototype slice call arguments

I know it is used to make arguments a real array, but I don’t understand what happens when using Array.prototype.slice.call(arguments)

13 Answers 13

What happens under the hood is that when .slice() is called normally, this is an Array, and then it just iterates over that Array, and does its work.

How is this in the .slice() function an Array? Because when you do:

. the object automatically becomes the value of this in the method() . So with:

. the [1,2,3] Array is set as the value of this in .slice() .

But what if you could substitute something else as the this value? As long as whatever you substitute has a numeric .length property, and a bunch of properties that are numeric indices, it should work. This type of object is often called an array-like object.

The .call() and .apply() methods let you manually set the value of this in a function. So if we set the value of this in .slice() to an array-like object, .slice() will just assume it’s working with an Array, and will do its thing.

Take this plain object as an example.

This is obviously not an Array, but if you can set it as the this value of .slice() , then it will just work, because it looks enough like an Array for .slice() to work properly.

As you can see in the console, the result is what we expect:

So this is what happens when you set an arguments object as the this value of .slice() . Because arguments has a .length property and a bunch of numeric indices, .slice() just goes about its work as if it were working on a real Array.

The arguments object is not actually an instance of an Array, and does not have any of the Array methods. So, arguments.slice(. ) will not work because the arguments object does not have the slice method.

Arrays do have this method, and because the arguments object is very similar to an array, the two are compatible. This means that we can use array methods with the arguments object. And since array methods were built with arrays in mind, they will return arrays rather than other argument objects.

So why use Array.prototype ? The Array is the object which we create new arrays from ( new Array() ), and these new arrays are passed methods and properties, like slice. These methods are stored in the [Class].prototype object. So, for efficiency sake, instead of accessing the slice method by (new Array()).slice.call() or [].slice.call() , we just get it straight from the prototype. This is so we don’t have to initialise a new array.

But why do we have to do this in the first place? Well, as you said, it converts an arguments object into an Array instance. The reason why we use slice, however, is more of a «hack» than anything. The slice method will take a, you guessed it, slice of an array and return that slice as a new array. Passing no arguments to it (besides the arguments object as its context) causes the slice method to take a complete chunk of the passed «array» (in this case, the arguments object) and return it as a new array.

Поиск по форуму
Расширенный поиск
К странице.

Илья Кантор, 28 мая 2009 — 12:29

Переменная, доступная внутри функции и содержащая аргументы и ссылку на саму функцию.

Описание, примеры

Локальная переменная arguments доступна внутри функций.

Вы можете обращаться к аргументу по номеру, начиная от 0. При этом arguments содержит не объявленные, а реально переданные аргументы.

Следующий пример выведет реально переданные три аргумента, несмотря на то, что в функции их всего два.

Кроме цифровых индексов, у arguments есть свойство length , такое же как у массива.

Благодаря этому можно вызывать функции с переменным числом параметров. В следующем примере функция возвращает сумму всех аргументов.

Несмотря на доступ по индексу и наличие свойства length , arguments не является массивом, т.е не принадлежит типу Array.

Поэтому для arguments нельзя напрямую вызвать методы этого класса:

Можно, однако, вызвать методы Array через apply/call:

Ссылка на функцию arguments.callee

Кроме аргументов, arguments содержит ссылку на выполняющуюся функцию.

Ее можно использовать для задания и чтения статических свойств.
В следующем примере для этого используется статическое свойство called .

Я даже не знал о такой переменной.

Подскажите если я вот так использую функцию она может отжирать много оперативки?

Спасибо за статью, даже не слышал о такой переменной, и когда она мне попалась при разработке анимации на сайте, не мог найти достойного описании. А тут как свет с небес, все стало ясно. Спасибо огромное, и респект сайту, дай бог Вам долгого существования, таких бы сайтов да побольше и в одном месте а не рыться в поисковике.

Благодарю за подобное описание функции! Я именно ее и искал.

«arguments содержит не объявленные, а реально переданные аргументы»
Это значит, что можно и не описывать аргументы т.е. вот так?:

function func() <
console.log(arguments[0]);
>

Почему то в описании функции массивов slice первый параметр обязателен, а в конструкции

функция slice вызывается без аргументов, и тем не менее возвращает массив, содержащий все переданные в функцию аргументы. Это нестыковка документации javascript?

или :
function func() <
func.called++
>

«Вы можете обращаться к аргументу по номеру, начиная от 0. При этом arguments содержит не объявленные, а реально переданные аргументы.

Следующий пример выведет реально переданные три аргумента, несмотря на то, что в функции их всего два.»

«Определимся с терминами». При объявлении функции указываются ПАРАМЕТРЫ, а не аргументы.
Параметр — это то, что ОБЪЯВЛЯЕТСЯ, аргумент — что ПЕРЕДАЕТСЯ. Слово «реально» в контексте «реально переданные» второй фразы лишнее.

Переменная, доступная внутри функции и содержащая аргументы и ссылку на саму функцию.»

Первое. Если аргумент — это значение, которое задается при вызове функции (по определению), то переменная arguments, скорее, содержит параметры, а не аргументы.

Второе. Элементарный анализ показывает, что при описании функции, использующей переменные arguments, стоит опустить указание параметров, (так как их может быть любое количество от 0 до n+1, где n — максимальный номер переменной arguments).
Получается, что в js нет процедур, их роль выполняют функции. Если функция возвращает значение (то есть, содержит оператор return), которое можно присвоить переменной, вызвав данную функцию, то это – функция в чистом виде. Если же она возвращает действие (без return), то эта функция по сути (де факто) является процедурой.
Так вот, в функциях-процедурах наряду с ненулевым может иметь и нулевое количество параметров.

Спешу себя опровергнуть. Если в определении функции используется переменная arguments, то ее можно вызывать с ЛЮБЫМ количеством аргументов!

Спасибо, хорошее описание. Но один вопрос: немного не ясно по поводу arguments.callee. Для чего это надо? Именно конкретно arguments.callee. Заранее благодарю за помощь

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

Мой вопрос из области использую, что то не зная, что это. Не могу взять в толк по какому принципу работает заимствование методов через Array.prototype.slice.call, в данном случае пример такой. Получаю массив элементов родителя, внутри которого совершен клик, но как именно работает этот метод? Объясните нубику плиз

  • Вопрос задан 17 сент.
  • 121 просмотр

call это метод который позволяет вызвать функцию и явно указать её контекст, то есть объект к которому эта функция будет иметь доступ по идентификатору this. Slice это метод массива с помощью которого можно получить копию части или всего массива.

Node.children принадлежит классу HTMLCollection, поэтому у него нету методов доступных массивам, хоть он и по структуре идентичен массиву. А slice копирует эту коллекцию только уже в виде массива, в результате чего к этому же самому набору элементов мы можем применить методы присущие массивам.

Зы: если у вас в переменной index должен лежать актуальный порядковый номер элемента, то совсем не обязательно для этого гонять slice+indexOf; для этого в объекте элемента есть соответствующее свойство. Хотя это говорят быстрее работает

Оцените статью