Отображение числа в два ближайших числа, кратные 2, начиная с заданного значения c - PullRequest
1 голос
/ 17 января 2020

Я пытаюсь придумать функцию / отображение от заданного числа n до двух чисел lo и hi. И lo, и hi имеют кратное 2, начиная со значения 6,25. И lo, и hi также имеют свойство lo <= n < hi.

По существу lo и hi являются двумя ближайшими к n значениями, образованными из 6.25 * (2^x), где x неизвестно.

Можно предположить, что n >= 6.25 ,

Вот некоторые примеры:

n = 10  -> [6.25, 12.5]
n = 12  -> [6.25, 12.5]
n = 13  -> [12.5, 25]
n = 25  -> [25, 50]
n = 40  -> [25, 50]
n = 50  -> [50, 100]
n = 300 -> [200, 400]
n = 400 -> [400, 800]
n = 413 -> [400, 800]
n = 500 -> [400, 800]

Это просто написать как oop в JavaScript, например:

const nearest = n => {
  let lo = 6.25;
  let hi = lo * 2;

  while (n >= hi) {
    lo *= 2;
    hi *= 2;
  }

  return [lo, hi];
}

Но в идеале Скорее, делайте это по-математике и не используйте петли. У кого-нибудь есть идеи?

Ответы [ 3 ]

3 голосов
/ 17 января 2020

Похоже, это то, что вам нужно. FYI Math.log2 не поддерживается в IE, поэтому вы можете включить полифилл.

// Polyfill
if (!Math.log2) {
    Math.log2 = function(x) {
      return Math.log(x) * Math.LOG2E;
    };
}

function mapValue(value) {
    var x = Math.floor(Math.log2(value / 6.25));
    
    var lo = 6.25 * Math.pow(2, x);
    var hi = lo * 2;
    
    return [lo, hi];
}

console.log([10, 12, 13, 25, 40, 50, 300, 400, 413, 500].map(mapValue));
3 голосов
/ 17 января 2020

Это должно сработать:

function nearest(n) {
    let exponent = Math.floor(Math.log2(n/6.25));
    let lo = Math.pow(2, exponent) * 6.25;
    let hi = lo * 2;

    return [lo, hi];
}

Журнал даст вам показатель степени для значения lo чуть ниже n. Обратите внимание, что вы должны «нормализовать» входные данные путем деления (и последующего умножения) на ваш коэффициент 6,25.

2 голосов
/ 17 января 2020

arr = [10, 12, 13, 25, 40, 50, 300, 400, 413, 500];

arr.forEach(a => {
  spanningRange = Math.max(2 ** Math.floor((Math.log(a / 100) / Math.log(2))) * 100, 6.25);
  console.log(`${a} -> [${spanningRange}, ${spanningRange * 2}]`)
});

но учтите, что ** является частью ES7, но в Google Chrome v79 и многих современных браузерах .

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...