Подтвердить что ты не робот

Javascript/angular - Прокрутка массива назад с помощью forEach

Есть ли способ прокрутки назад через массив с помощью forEach (а не какой-либо другой тип цикла, я знаю, как это сделать с помощью стандартных/стандартных способов) и без фактического обращения к самому массиву?

4b9b3361

Ответ 1

var arr = [1, 2, 3];

arr.slice().reverse().forEach(function(x) {
    console.log(x);
})

напечатает:

3
2
1

arr по-прежнему будет [1, 2, 3], .slice() создает мелкую копию.

Ответ 2

Нет, forEach обрабатывает только массив через массив. Таким образом, вам нужно будет сделать что-то еще, о чем вы сказали в своем вопросе, был вне сферы действия.

Я могу представить два варианта, которые просто используют прекурсоры для использования forEach (поэтому они не используют цикл for или другой тип цикла). Я не знаю, будут ли они недоступны или нет, так вот они:

  • Скопируйте массив и отмените копию, затем используйте forEach на нем

  • Используйте Object.keys, чтобы получить индексы, отмените их, а затем используйте forEach на нем (который будет прокручивать индексы, а не значения, но затем мы можем посмотреть их)

Здесь # 1:

slice копирует массив (мелкая копия, поэтому вряд ли будет стоить дорого), тогда мы отменим его, затем forEach:

var a = ['one', 'two', 'three'];
a.slice().reverse().forEach(function(entry) {
    snippet.log(entry);
});
snippet.log("Proof that a is not, itself, reversed: " +
            JSON.stringify(a));
<!-- Script provides the `snippet` object, see http://meta.stackexchange.com/a/242144/134069 -->
<script src="http://tjcrowder.github.io/simple-snippets-console/snippet.js"></script>

Ответ 3

Это может быть выполнено относительно кратко с использованием обратного метода, метода forEach и (если используется ES6) функции стрелки

var someArray = ["a","b","c","d"];
someArray.reverse().forEach(arrayItem =>
    console.log(arrayItem)
)

Если вы не используете ES6, решение будет примерно таким же, только без функции стрелки.

var someArray = ["a","b","c","d"];
someArray.reverse().forEach(function(arrayItem) {
    console.log(arrayItem)
})

Оба выведут на консоль:

d
c    
b
a

Ответ 4

Пока браузеры, похоже, не оптимизировали функцию Array.forEach. С небольшим усилием вы можете написать простой polyfill, который выполняет метод Array.forEach, по крайней мере, от 10 до 1.

Итак, вы можете создать свой собственный Array.revEach и превзойти его родной Array.forEach, подумал, что я надеюсь, что браузеры скоро выйдут на очень медленную производительность Array.forEach и сделают необходимость polyfill существующих существующих методов, а не необходимо.

Для Array.revEach out выполняется Array.forEach, выполняемое в 17 раз быстрее на "Chrome 46.0.2490.22 beta-m"

if (Array.prototype.revEach === undefined) { 
    Object.defineProperty(Array.prototype, 'revEach', { 
        writable : false,
        enumerable : false,
        configurable : false,
        value : function (func) {
            var i;
            var len = this.length-1;
            for (i = len; i >= 0; i--) {
                func(this[i], i, this);
            }
        }
    });
}

Просто добавьте фактическое официальное polyfill, измененное для обратного. Комментарии показывают мои изменения.

// Production steps of ECMA-262, Edition 5, 15.4.4.18
// Reference: http://es5.github.io/#x15.4.4.18
// Modified by Blindman67 to revEach
if (!Array.prototype.revEach) {   // name changed
  Array.prototype.revEach = function(callback, thisArg) { // name changed
    var T;  // k defined where len was
    if (this == null) {
      throw new TypeError(' this is null or not defined');
    }
    var O = Object(this);
    var k = (O.length >>> 0)-1;  // set k (counter) ToUint32
                                 // len var removed
    if (typeof callback !== "function") {
      throw new TypeError(callback + ' is not a function');
    }
    if (arguments.length > 1) {
      T = thisArg;
    }
    while (k >= 0) {  // reverse condition
      var kValue;
      if (k in O) {
        kValue = O[k];
        callback.call(T, kValue, k, O);
      }
      k--;  // dec counter
    }
  };
}

Ответ 5

У array.forEach есть 3 параметра. Вы можете использовать их, чтобы эффективно forEach назад.

var arr = [1, 2, 3];

    arr.forEach(function(x, index, the_array) {
        let x_prime = the_array[the_array.length-1-index]
        console.log(x_prime);
    })

распечатает

3
2
1

Ответ 6

Просто используйте для цикла. Начните с конца массива и идите назад оттуда.

const array = ['blastoff', 1, 2, 3];

for (let index = array.length - 1; index >= 0; index--) {
  const element = array[index];
  console.log(element);
}

Ответ 7

Существует аналогичный метод массива, который имеет обратный счетчик часть, reduce приходит вместе с reduceRight:

const array = ['alpha', 'beta', 'gamma'];

array.reduceRight((_, elem) => console.log(elem), null);