17

Есть ли в JavaScript метод, аналогичный "range()", для генерации диапазона в заданных границах?

13

Описание проблемы:

В PHP есть функция range(), которая позволяет получать диапазон чисел или символов, передавая нижнюю и верхнюю границы. Например:

range(1, 3); // Array(1, 2, 3)
range("A", "C"); // Array("A", "B", "C")

Однако, существует ли встроенная функция, аналогичная range(), в чистом JavaScript? Если такой функции нет, каким образом можно реализовать подобный функционал?

5 ответ(ов)

1

Вот моё мнение по этому вопросу:

function range(start, end) {
  return Array.apply(0, Array(end - start))
    .map((element, index) => index + start);
}

В этом коде используется метод Array.apply() для создания массива длиной end - start, а затем с помощью map() каждый элемент заполняется значениями, начиная с start и заканчивая end - 1. Обратите внимание, что я изменил end - 1 на end - start, чтобы правильно заполнить массив. Такой подход позволяет вам создавать последовательность чисел от start до end - 1, но я бы рекомендовал также рассмотреть более простые способы создания диапазона, например, с использованием цикла или метода Array.from() для более понятного кода.

0

Да, в JavaScript действительно нет функции range(), как в PHP, поэтому нам нужно создать эту функцию. Это довольно просто, я напишу несколько однострочных функций для вас и разделю их на числовые и алфавитные диапазоны.

Для чисел:

function numberRange(start, end) {
  return new Array(end - start).fill().map((d, i) => i + start);
}

Вызывайте её так:

numberRange(5, 10); //[5, 6, 7, 8, 9]

Для алфавитов:

function alphabetRange(start, end) {
  return new Array(end.charCodeAt(0) - start.charCodeAt(0)).fill().map((d, i) => String.fromCharCode(i + start.charCodeAt(0)));
}

И вызывайте её так:

alphabetRange('c', 'h'); //["c", "d", "e", "f", "g"]

Если у вас есть дополнительные вопросы или вам нужно что-то конкретное, не стесняйтесь задавать их!

0

Функция Array.range создает массив значений в заданном диапазоне. Давайте разберем, как она работает.

Array.range = function(a, b, step){
    var A = [];
    if(typeof a == 'number'){
        A[0] = a; // Начинаем массив с первого элемента 'a'
        step = step || 1; // Если шаг не задан, используем 1 как значение по умолчанию
        while(a + step <= b){ // Пока текущее значение 'a' плюс шаг не больше 'b'
            A[A.length]= a += step; // Увеличиваем 'a' на шаг и добавляем в массив
        }
    }
    else {
        var s = 'abcdefghijklmnopqrstuvwxyz'; // Строка со всеми строчными буквами
        if(a === a.toUpperCase()){ // Проверяем, если 'a' в верхнем регистре
            b = b.toUpperCase(); // Приводим 'b' к верхнему регистру
            s = s.toUpperCase(); // Приводим строку к верхнему регистру
        }
        s = s.substring(s.indexOf(a), s.indexOf(b) + 1); // Извлекаем подстроку от 'a' до 'b'
        A = s.split(''); // Превращаем подстроку в массив
    }
    return A; // Возвращаем получившийся массив
}

Примеры использования:

  1. Array.range(0, 10);

    • Возвращает массив с числами от 0 до 10: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10].
  2. Array.range(-100, 100, 20);

    • Возвращает массив с шагом 20 в диапазоне от -100 до 100: [-100, -80, -60, -40, -20, 0, 20, 40, 60, 80, 100].
  3. Array.range('A', 'F');

    • Возвращает массив букв в диапазоне от 'A' до 'F': ['A', 'B', 'C', 'D', 'E', 'F'].
  4. Array.range('m', 'r');

    • Возвращает массив букв от 'm' до 'r': ['m', 'n', 'o', 'p', 'q', 'r'].

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

0

Вот перевод на русский язык, стилизованный как ответ на вопрос на StackOverflow:

С диапазоном/шагом

Самый компактный вариант в одну строку:

[...Array(N)].map((_, i) => from + i * step);

Примеры и альтернативы

[...Array(10)].map((_, i) => 4 + i * 2);
//=> [4, 6, 8, 10, 12, 14, 16, 18, 20, 22]

Array.from(Array(10)).map((_, i) => 4 + i * 2);
//=> [4, 6, 8, 10, 12, 14, 16, 18, 20, 22]

Array.from(Array(10).keys()).map(i => 4 + i * 2);
//=> [4, 6, 8, 10, 12, 14, 16, 18, 20, 22]

[...Array(10).keys()].map(i => 4 + i * -2);
//=> [4, 2, 0, -2, -4, -6, -8, -10, -12, -14]

Array(10).fill(0).map((_, i) => 4 + i * 2);
//=> [4, 6, 8, 10, 12, 14, 16, 18, 20, 22]

Array(10).fill().map((_, i) => 4 + i * -2);
//=> [4, 2, 0, -2, -4, -6, -8, -10, -12, -14]

Функция диапазона

const range = (from, to, step) =>
  [...Array(Math.floor((to - from) / step) + 1)].map((_, i) => from + i * step);

range(0, 9, 2);
//=> [0, 2, 4, 6, 8]

// Также можно добавить функцию range в класс Array (но это не рекомендуется)
Array.range = (from, to, step) =>
  [...Array(Math.floor((to - from) / step) + 1)].map((_, i) => from + i * step);

Array.range(2, 10, 2);
//=> [2, 4, 6, 8, 10]

Array.range(0, 10, 1);
//=> [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10]

Array.range(2, 10, -1);
//=> []

Array.range(3, 0, -1);
//=> [3, 2, 1, 0]

В виде итераторов

class Range {
  constructor(total = 0, step = 1, from = 0) {
    this[Symbol.iterator] = function* () {
      for (let i = 0; i < total; yield from + i++ * step) {}
    };
  }
}

[...new Range(5)]; // Пять элементов
//=> [0, 1, 2, 3, 4]
[...new Range(5, 2)]; // Пять элементов с шагом 2
//=> [0, 2, 4, 6, 8]
[...new Range(5, -2, 10)]; // Пять элементов с шагом -2 начиная с 10
//=>[10, 8, 6, 4, 2]
[...new Range(5, -2, -10)]; // Пять элементов с шагом -2 начиная с -10
//=> [-10, -12, -14, -16, -18]

// Также работает с циклом for..of
for (i of new Range(5, -2, 10)) console.log(i);
// 10 8 6 4 2

Только генераторы

const Range = function* (total = 0, step = 1, from = 0) {
  for (let i = 0; i < total; yield from + i++ * step) {}
};

Array.from(Range(5, -2, -10));
//=> [-10, -12, -14, -16, -18]

[...Range(5, -2, -10)]; // Пять элементов с шагом -2 начиная с -10
//=> [-10, -12, -14, -16, -18]

// Также работает с циклом for..of
for (i of Range(5, -2, 10)) console.log(i);
// 10 8 6 4 2

// Ленивый способ
const number0toInf = Range(Infinity);
number0toInf.next().value;
//=> 0
number0toInf.next().value;
//=> 1
// ...

С диапазоном и шагами/дельтой

Используя итераторы:

class Range2 {
  constructor(to = 0, step = 1, from = 0) {
    this[Symbol.iterator] = function* () {
      let i = 0,
        length = Math.floor((to - from) / step) + 1;
      while (i < length) yield from + i++ * step;
    };
  }
}
[...new Range2(5)]; // Первые 5 целых чисел
//=> [0, 1, 2, 3, 4]

[...new Range2(5, 2)]; // От 0 до 5 с шагом 2
//=> [0, 2, 4]

[...new Range2(5, -2, 10)]; // От 10 до 5 с шагом -2
//=> [10, 8, 6]

Используя генераторы:

const Range2 = function* (to = 0, step = 1, from = 0) {
  let i = 0,
    length = Math.floor((to - from) / step) + 1;
  while (i < length) yield from + i++ * step;
};

[...Range2(5, -2, 10)]; // От 10 до 5 с шагом -2
//=> [10, 8, 6]

let even4to10 = Range2(10, 2, 4);
even4to10.next().value;
//=> 4
even4to10.next().value;
//=> 6
even4to10.next().value;
//=> 8
even4to10.next().value;
//=> 10
even4to10.next().value;
//=> undefined

Для TypeScript

class _Array<T> extends Array<T> {
  static range(from: number, to: number, step: number): number[] {
    return Array.from(Array(Math.floor((to - from) / step) + 1)).map(
      (v, k) => from + k * step
    );
  }
}
_Array.range(0, 9, 1);

Генерация списка символов в одну строку

const charList = (a,z,d=1)=>(a=a.charCodeAt(),z=z.charCodeAt(),[...Array(Math.floor((z-a)/d)+1)].map((_,i)=>String.fromCharCode(a+i*d)));

console.log("от A до G", charList('A', 'G'));
console.log("от A до Z с шагом 2", charList('A', 'Z', 2));
console.log("в обратном порядке от Z до P", charList('Z', 'P', -1));
console.log("от 0 до 5", charList('0', '5', 1));
console.log("от 9 до 5", charList('9', '5', -1));
console.log("от 0 до 8 с шагом 2", charList('0', '8', 2));
console.log("от α до ω", charList('α', 'ω'));
console.log("индийские символы от क до ह", charList('क', 'ह'));
console.log("русские символы от А до Я", charList('А', 'Я'));

Для TypeScript:

const charList = (p: string, q: string, d = 1) => {
  const a = p.charCodeAt(0),
    z = q.charCodeAt(0);
  return [...Array(Math.floor((z - a) / d) + 1)].map((_, i) =>
    String.fromCharCode(a + i * d)
  );
};
0

В данном коде создаётся функция range, которая принимает два аргумента l и r. Она возвращает массив, содержащий последовательные числа от l до r - 1. Вот как работает данный код:

  1. new Array(r - l) — создаёт новый массив длиной, равной разнице между r и l.
  2. .fill() — заполняет созданный массив "пустыми" значениями, чтобы метод map мог быть применён.
  3. .map((_, k) => k + l) — использует метод map для преобразования каждого элемента массива. Здесь переменная _ представляет текущее значение (мы её не используем), а k — индекс, который будет от 0 до r-l-1. Мы добавляем l к индексу, чтобы получить нужные значения.

Пример использования функции:

console.log(range(3, 7)); // Выведет [3, 4, 5, 6]

Таким образом, функция range(l, r) эффективно генерирует последовательность чисел в указанном диапазоне.

Чтобы ответить на вопрос, пожалуйста, войдите или зарегистрируйтесь