альтернатива parseInt - PullRequest
       14

альтернатива parseInt

10 голосов
/ 27 февраля 2009

Во-первых - мое описание;)

У меня есть ответ XSONHttpRequests JSON от сервера. Драйвер MySQL выводит все данные в виде строки, а PHP возвращает их как есть, поэтому любое целое число возвращается в виде строки, поэтому:

Есть ли быстрая альтернатива (взлом) для функции parseInt () в JS, которая может анализировать чистую числовую строку, например

var foo = {"bar": "123"};
...
foo.bar = parseInt(foo.bar); // (int) 123

Ответы [ 11 ]

37 голосов
/ 27 февраля 2009

Для преобразования в целое число просто используйте унарный оператор +, это должен быть самый быстрый способ:

var int = +string;

Преобразования в другие типы могут быть выполнены аналогичным образом:

var string = otherType + "";
var bool = !!anything;

Подробнее .

12 голосов
/ 27 февраля 2009

Приведение типов в JavaScript выполняется через функции конструктора встроенных типов без new, т. Е.

foo.bar = Number(foo.bar);

Это отличается от parseInt() в нескольких отношениях:

  • ведущие нули не активируют восьмеричный режим
  • будут также проанализированы значения с плавающей запятой
  • вся строка анализируется, т. Е. Если она содержит дополнительные нечисловые символы, возвращаемое значение будет NaN
8 голосов
/ 27 февраля 2009

Во-первых, вы на самом деле задокументировали, что это медленно и вызывает проблемы? В противном случае, я бы не стал искать решение, потому что проблемы действительно нет.

Во-вторых, я бы предположил, что поскольку parseInt является нативным JS-методом, он будет реализован очень быстро и, возможно, на родном языке виртуальной машины (вероятно, C, в зависимости от браузера / виртуальной машины). , Я думаю, у вас могут возникнуть проблемы с созданием более быстрого метода из чистого JS. =)

Конечно, я не гуру JS, поэтому я не знаю наверняка, но это то, что говорит мне моя интуиция, и, как правило, является стандартным ответом на вопрос: «Как бы я сделал более быструю альтернативу для libraryFunction?» ()?» вопросы.

6 голосов
/ 27 февраля 2009

Приведите его к int в PHP, прежде чем json_encode() it:

$foo->bar = (int)$foo->bar;
print('var foo = ' . json_encode($foo));

Кстати, при использовании parseInt рекомендуется всегда указывать второй параметр, если только вы не хотите, чтобы строка, начинающаяся с 0, интерпретировалась как восьмеричная и т. Д.:

parseInt('010', 10); // 10
2 голосов
/ 27 февраля 2009

Вы не станете лучше, чем parseInt, но настоящая ошибка в том, что PHP предоставляет то, что должно быть числом в виде строки.

И то же самое сказал Дэниел - не ищите таких микрооптимизаций, пока не сравните свой код и не обнаружите, что оно того стоит.

2 голосов
/ 27 февраля 2009

Конструктор Number также существует, но он должен быть таким же, как parseInt в плане скорости (как уже было сказано, вы должны исправить часть PHP вместо части javascript):

var i = "123";
i = new Number(i); // Number numeric wrapper
var j = "123";
j = Number(j); // Number primitive

Кстати, если кому-то интересно, я по любопытству искал реализацию parseInt для V8 (Google chrome), а здесь в коде Google *

1 голос
/ 13 ноября 2014

Быстрый ярлык для разбора

("78.5" | 0) //bitwise or forces the string to parse as int

Это то, что ASM использует для представления целых чисел в js.

0 голосов
/ 17 февраля 2019

Это решение быстрее, чем parseInt (), если вы анализируете строки десятичного целого числа длиной не более 20. Для некоторых браузеров вы все равно можете работать быстрее, чем parseInt (), до 33 цифр. Кроме того, вы все равно будете быстрее, чем автоматически.

Это потому, что parseInt () для браузера действительно требуется некоторое время, чтобы прогреться, поэтому, если вы используете только простой метод для анализа, вы бьете его некоторое время, пока он не догонит. Не используйте это для nodeJS. При запуске parseInt () из nodeJS время запуска намного меньше, чем при запуске из браузера.

45 - это знак «-» в ASCII, 43 - это знак «+» в ASCII. 48 - это «0». Только от 48 до 57 или 48 становятся 0 - 9 (в их порядке). Нет других чисел xor 48 дает 0-9.

Это вернет undefined, если строка не является допустимой десятичной целочисленной строкой или если строка пуста. Он выдает строку со значением «Не строка», если входные данные не имеют тип string.

var toNumber = function (input) {
    if ( typeof input !== "string" ) throw "Not a string";

    var length = input.length;
    if ( length === 0 ) return;
    var c1 = input.charCodeAt(0); 

    if ( c1 === 45 || c1 === 43 ){
        if ( length === 1 ) return;
        var start = 1;
    } else {
        var start = 0;
    }

    var out = 0, c;    
    while( start < length && input.charCodeAt(start) === 48 ) start++;

    for ( ; start < length; start++){
        c = input.charCodeAt(start) ^ 48;
        if ( c > 9 ) return;
        out = (out * 10) + c;
    }

    if ( c1 === 45 ) return out * -1;
    return out;
}
0 голосов
/ 27 февраля 2009

Приведение происходит немного быстрее, чем анализ, но медленнее, чем поиск.

Кроме того, в Firefox самым быстрым методом оказывается parseInt () с последующим поиском. Firefox также оказался в 6 раз быстрее, чем IE. Интересно.

Классная идея с использованием унарного оператора. В Firefox это оказалось сравнимым с parseInt (). В IE это оказался самый быстрый способ.

0 голосов
/ 27 февраля 2009

Как медленно это может быть? Сколько раз в секунду вызывается этот процесс? Сколько существует различных числовых возвращаемых значений? Я собрал сценарий и проверил 100 000 номеров. Разбор их из строк занял 687мс. Поиск их в массиве занял 541мс. Это очень небольшое улучшение. Я согласен с другими постерами. Вы не можете получить лучше, чем собственный метод parseInt ().

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