Какое наибольшее целочисленное значение в JavaScript может быть достигнуто числом без потери точности?

951

Это определяется языком? Есть ли определенный максимум? Это отличается в разных браузерах?

TALlama
источник
5
Вам не нужно зависеть от ограничений JS с библиотеками, такими как github.com/MikeMcl/big.js , см., Например, здесь для проверки надежности
Дмитрий Зайцев
2
Какое наибольшее целочисленное значение вы можете использовать с big.js?
Джордж
@ Джордж Вот API big.js: mikemcl.github.io/big.js/#dp
simhumileco
Вопрос не имеет смысла. Что это означает, что число «идет» к целочисленному значению? Если вы просто хотите спросить, какое наибольшее целое число вы можете представить в JS, самое высокое (конечное) число само является целым числом.
Веки
@DmitriZaitsev Нам больше не нужно зависеть от внешних библиотек (по крайней мере, в некоторых браузерах). 1n << 10000nэто действительно очень большое целое число, без потери точности, без каких-либо зависимостей (и, разумеется, даже близко к пределу).
Амадан

Ответы:

868

JavaScript имеет два типа чисел: Numberи BigInt.

Наиболее часто используемым типом чисел Numberявляется 64-битное число IEEE 754 с плавающей запятой .

Наибольшее точное целочисленное значение этого типа Number.MAX_SAFE_INTEGER:

  • 2 53 -1 или
  • +/- 9 007 199 254 740 991 или
  • девять квадриллионов семь триллионов сто девяносто девять миллиардов двести пятьдесят четыре миллиона семьсот сорок тысяч девятьсот девяносто один

Для сравнения: один квадриллион байтов - это петабайт (или тысяча терабайт).

«Безопасный» в данном контексте относится к способности точно представлять целые числа и правильно их сравнивать.

Из спецификации:

Обратите внимание, что все положительные и отрицательные целые числа, величина которых не превышает 2 53 , представимы в Numberтипе (действительно, целое число 0 имеет два представления: +0 и -0).

Чтобы безопасно использовать целые числа больше этого, вам нужно использовать BigInt, у которого нет верхней границы.

Обратите внимание, что побитовые операторы и операторы сдвига работают с 32-разрядными целыми числами, поэтому в этом случае максимальное безопасное целое число составляет 2 31 -1 или 2 147 483 647.

const log = console.log
var x = 9007199254740992
var y = -x
log(x == x + 1) // true !
log(y == y - 1) // also true !

// Arithmetic operators work, but bitwise/shifts only operate on int32:
log(x / 2)      // 4503599627370496
log(x >> 1)     // 0
log(x | 1)      // 1


Техническое примечание по вопросу числа 9,007,199,254,740,992: существует точное представление этого значения IEEE-754, и вы можете присвоить и прочитать это значение из переменной, поэтому для очень тщательно выбранных приложений в области целых чисел, меньших или равных это значение, вы можете рассматривать это как максимальное значение.

В общем случае вы должны рассматривать это значение IEEE-754 как неточное, поскольку неясно, кодирует ли оно логическое значение 9,007,199,254,740,992 или 9,007,199,254,740,993.

Джимми
источник
75
Это кажется правильным, но есть ли место, где это определено, например, MAX_INT C или Java Integer.MAX_VALUE?
TALlama
48
4294967295 === Math.pow(2,32) - 1;
CoolAJ86
13
Итак, какое наименьшее и наибольшее целое число мы можем использовать для обеспечения точной точности?
Pacerier
38
Возможно, стоит отметить, что в javascript нет фактических (int). Каждый экземпляр Number является (float) или NaN.
Свекла-Свекла
53
9007199254740992 на самом деле не максимальное значение, последний бит здесь уже принят равным нулю, и поэтому вы потеряли 1 бит точности. Настоящий безопасный номер - 9007199254740991 (Number.MAX_SAFE_INTEGER)
Виллем Д'Азелер
461

> = ES6:

Number.MIN_SAFE_INTEGER;
Number.MAX_SAFE_INTEGER;

<= ES5

Из ссылки :

Number.MAX_VALUE;
Number.MIN_VALUE;

Питер Бейли
источник
23
Я отредактировал вопрос, чтобы быть более точным в том, что нужно получить максимальные целочисленные значения, а не только максимальное числовое значение. Извините за путаницу, здесь.
TALlama
5
Гарантированный ли возвращаемый результат одинаков во всех браузерах?
Пейсер
7
Обратите внимание, что Number.MIN_VALUEэто наименьшее возможное положительное число. Мере значение (то есть меньше , чем все остальное), вероятно -Number.MAX_VALUE.
Майкл Шепер
34
ES6 представляет Number.MIN_SAFE_INTEGERиNumber.MAX_SAFE_INTEGER
суперлуки
2
Так, в этом случае, мы должны отклонить ответ, потому что он не подходит для обновленного вопроса, или оставить его, потому что Питер Бейли был прав в тот момент, когда на него был дан ответ?
ракеты отправляются
112

Это 2 53 == 9 007 199 254 740 992. Это потому, что Numbers хранятся в виде плавающей запятой в 52-битной мантиссе.

Минимальное значение -2 53 .

Это делает некоторые забавные вещи, происходящие

Math.pow(2, 53) == Math.pow(2, 53) + 1
>> true

И тоже может быть опасно :)

var MAX_INT = Math.pow(2, 53); // 9 007 199 254 740 992
for (var i = MAX_INT; i < MAX_INT + 2; ++i) {
    // infinite loop
}

Дополнительная литература: http://blog.vjeux.com/2010/javascript/javascript-max_int-number-limits.html

Vjeux
источник
1
хотя никто и никогда не достигнет конца цикла for в разумные сроки, вы можете сказатьi += 1000000000
ninjagecko
2
@ninjagecko, он начинает с MAX_INT, так что конец тут же. Также использование i + = 1000000000 сделало бы его больше не бесконечным циклом. Попробуй это.
Тед Бигхам
@TedBigham: Ой, слишком быстро через это было готово. Спасибо, что поправили меня дважды.
Ninjagecko
См. Аргумент Джимми для 9,007,199,254,740,991 вместо 9,007,199,254,740,992 здесь . Это, в сочетании с моим продолжением, кажется убедительным.
TJ Crowder
60

В JavaScript есть номер с именем Infinity.

Примеры:

(Infinity>100)
=> true

// Also worth noting
Infinity - 1 == Infinity
=> true

Math.pow(2,1024) === Infinity
=> true

Это может быть достаточно для некоторых вопросов, касающихся этой темы.

BananaNeil
источник
25
Что-то подсказывает мне, что бесконечность не считается целым числом. :)
devios1
7
Но достаточно инициализировать minпеременную, когда вы ищете минимальное значение.
Джек
9
Обратите внимание, чтоInfinity - 1 === Infinity
H.Wolper
2
также (Infinity <100) => false и Math.pow (2,1024) === Бесконечность
Sijav
6
Также ничего не стоит, что он справляется и с отрицательной бесконечностью. Итак1 - Infinity === -Infinity
dmccabe
41

Ответ Джимми правильно представляет непрерывный целочисленный спектр JavaScript как от -9007199254740992 до 9007199254740992 включительно (извините, 9007199254740993, вы можете подумать, что вы 9007199254740993, но вы ошибаетесь! Демонстрация ниже или в jsfiddle ).

console.log(9007199254740993);

Тем не менее, нет ответа, который находит / доказывает это программно (кроме того, на который ссылается CoolAJ86 в своем ответе , который закончится через 28,56 лет;), так что вот немного более эффективный способ сделать это (точнее, это более эффективно примерно на 28,559999999968312 лет :) вместе с испытательной скрипкой :

/**
 * Checks if adding/subtracting one to/from a number yields the correct result.
 *
 * @param number The number to test
 * @return true if you can add/subtract 1, false otherwise.
 */
var canAddSubtractOneFromNumber = function(number) {
    var numMinusOne = number - 1;
    var numPlusOne = number + 1;
    
    return ((number - numMinusOne) === 1) && ((number - numPlusOne) === -1);
}

//Find the highest number
var highestNumber = 3; //Start with an integer 1 or higher

//Get a number higher than the valid integer range
while (canAddSubtractOneFromNumber(highestNumber)) {
    highestNumber *= 2;
}

//Find the lowest number you can't add/subtract 1 from
var numToSubtract = highestNumber / 4;
while (numToSubtract >= 1) {
    while (!canAddSubtractOneFromNumber(highestNumber - numToSubtract)) {
        highestNumber = highestNumber - numToSubtract;
    }
    
    numToSubtract /= 2;
}        

//And there was much rejoicing.  Yay.    
console.log('HighestNumber = ' + highestNumber);

Briguy37
источник
8
@ CoolAJ86: Lol, я с нетерпением жду 15 марта 2040 года. Если наши числа совпадают, мы должны устроить вечеринку :)
Briguy37
var x = Math.pow (2,53) -3; while (x! = x + 1) x ++; -> 9007199254740991
MickLH
@MickLH: я получаю 9007199254740992 с этим кодом . Какой движок JavaScript вы используете для тестирования?
Briguy37
Вы получаете 9007199254740992 со своим собственным кодом, я не использовал окончательное значение x, но окончательное вычисление x ++ по параноидальным причинам. Google Chrome, кстати.
MickLH
@MickLH: оценка x++дает вам значение x до того, как произошло увеличение, что, вероятно, объясняет расхождение. Если вы хотите, чтобы выражение оценивалось так же, как и конечное значение x, вы должны изменить его на ++x.
peterflynn
32

Быть в безопасности

var MAX_INT = 4294967295;

аргументация

Я думал, что я был бы умен и нашел бы ценность x + 1 === xс более прагматичным подходом.

Моя машина может считать только 10 миллионов в секунду или около того ... поэтому я отправлю ответ с окончательным ответом через 28,56 лет.

Если вы не можете ждать так долго, я готов поспорить, что

  • Большинство ваших петель не работают в течение 28,56 лет
  • 9007199254740992 === Math.pow(2, 53) + 1 достаточно доказательств
  • Вы должны придерживаться , 4294967295который , Math.pow(2,32) - 1как ожидается , чтобы избежать проблем с битным перекладывания

Нахождение x + 1 === x:

(function () {
  "use strict";

  var x = 0
    , start = new Date().valueOf()
    ;

  while (x + 1 != x) {
    if (!(x % 10000000)) {
      console.log(x);
    }

    x += 1
  }

  console.log(x, new Date().valueOf() - start);
}());
CoolAJ86
источник
4
не можете ли вы просто начать это в 2 ^ 53 - 2, чтобы проверить? (да, вы можете, я только что попробовал, даже с -3, чтобы быть безопасным: var x = Math.pow (2,53) -3; while (x! = x + 1) x ++;) -> 9007199254740991
MickLH
Хороший ответ! Более того, я знаю, что значение установлено, но почему бы не использовать бинарный поиск для его поиска?
Higuaro
1
Что в этом весёлого? Кроме того, @ Briguy37 опередил меня: stackoverflow.com/a/11639621/151312
CoolAJ86
обратите внимание, что этот «безопасный» MAX_INT на основе 32 битов не будет работать при сравнении со значениями даты. 4294967295 так вчера!
Джерри
1
Ответ «На всякий случай: var MAX_INT = 4294967295;» не с чувством юмора Если вы не сдвигаете биты, не беспокойтесь об этом (если только вам не нужно int больше 4294967295, в этом случае вам, вероятно, следует сохранить его как строку и использовать библиотеку bigint).
CoolAJ86
29

Краткий ответ «это зависит».

Если вы где-либо используете побитовые операторы (или если вы ссылаетесь на длину массива), диапазоны:

БЕЗЗНАКОВЫЙ: 0…(-1>>>0)

Подпись: (-(-1>>>1)-1)…(-1>>>1)

(Бывает, что побитовые операторы и максимальная длина массива ограничены 32-битными целыми числами.)

Если вы не используете побитовые операторы или не работаете с длинами массива:

Подпись: (-Math.pow(2,53))…(+Math.pow(2,53))

Эти ограничения налагаются внутренним представлением типа «Число», которое в целом соответствует представлению с плавающей точкой двойной точности IEEE 754. (Обратите внимание, что в отличие от типичных целых чисел со знаком, величина отрицательного предела такая же, как величина положительного предела, из-за характеристик внутреннего представления, которое фактически включает отрицательный 0!)

danorton
источник
Это ответ, на который я хотел бы наткнуться, о том, как преобразовать X в 32-разрядное целое или целое число без знака. Подтвердил ваш ответ за это.
Чарли Аффумигато
29

ECMAScript 6:

Number.MAX_SAFE_INTEGER = Math.pow(2, 53)-1;
Number.MIN_SAFE_INTEGER = -Number.MAX_SAFE_INTEGER;
Вайкит кунг
источник
1
Остерегайтесь, это (пока) не поддерживается всеми браузерами! Сегодня iOS (даже не Chrome), Safari и IE не нравятся.
Cregox
5
Пожалуйста, внимательно прочитайте ответ, мы не используем реализацию Number.MAX_SAFE_INTEGER по умолчанию в ECMAScript 6, мы определяем его с помощью Math.pow (2, 53) -1
WaiKit Kung
Я думал, что это просто ссылка на то, как это реализовано в ECMA 6! Я думаю, что мой комментарий все еще действителен. Все дело в контексте. ;)
Cregox
3
Надежно ли рассчитывать MAX_SAFE_INTEGERво всех браузерах, работая в обратном направлении? Стоит ли двигаться вперед? То есть Number.MAX_SAFE_INTEGER = 2 * (Math.pow (2, 52) - 1) + 1;
KJV
Это Math.pow(2, 53)-1безопасная операция? Это больше, чем наибольшее безопасное целое число.
ioquatix
21

Многие ответы от прежних времен показали результат trueот 9007199254740992 === 9007199254740992 + 1проверить , что 9 007 199 254 740 991 максимальные и безопасное целое.

Что если мы продолжим накопление:

input: 9007199254740992 + 1  output: 9007199254740992  // expected: 9007199254740993
input: 9007199254740992 + 2  output: 9007199254740994  // expected: 9007199254740994
input: 9007199254740992 + 3  output: 9007199254740996  // expected: 9007199254740995
input: 9007199254740992 + 4  output: 9007199254740996  // expected: 9007199254740996

Мы могли бы узнать, что среди чисел больше 9 007 199 254 740 992 , только четное число представимо .

Это вводная часть, чтобы объяснить, как 64-битный двоичный формат двойной точности работает на этом. Давайте посмотрим, как 9 007 199 254 740 992 будет храниться (представляться) с использованием этого двоичного формата.

Используя краткую версию, чтобы продемонстрировать это от 4 503 599 627 370 496 :

  1 . 0000 ---- 0000  *  2^52            =>  1  0000 ---- 0000.  
     |-- 52 bits --|    |exponent part|        |-- 52 bits --|

В левой части стрелки у нас есть битовое значение 1 и смежная точка радиуса , затем, умножая 2^52, мы вправо смещаем точку радиуса 52 шага, и она идет до конца. Теперь мы получаем 4503599627370496 в двоичном виде.

Теперь мы начинаем накапливать 1 к этому значению, пока все биты не будут установлены в 1, что равно 9 007 199 254 740 991 в десятичном виде.

  1 . 0000 ---- 0000  *  2^52  =>  1  0000 ---- 0000.  
                       (+1)
  1 . 0000 ---- 0001  *  2^52  =>  1  0000 ---- 0001.  
                       (+1)
  1 . 0000 ---- 0010  *  2^52  =>  1  0000 ---- 0010.  
                       (+1)
                        . 
                        .
                        .
  1 . 1111 ---- 1111  *  2^52  =>  1  1111 ---- 1111. 

Теперь, поскольку в 64-битном двоичном формате двойной точности он строго выделяет 52 бита для дроби, больше нет битов, которые можно перенести для добавления еще 1, поэтому мы можем установить все биты обратно в 0 и манипулировать показательной частью:

  |--> This bit is implicit and persistent.
  |        
  1 . 1111 ---- 1111  *  2^52      =>  1  1111 ---- 1111. 
     |-- 52 bits --|                     |-- 52 bits --|

                          (+1)
                                     (radix point has no way to go)
  1 . 0000 ---- 0000  *  2^52 * 2  =>  1  0000 ---- 0000. * 2  
     |-- 52 bits --|                     |-- 52 bits --|

  =>  1 . 0000 ---- 0000  *  2^53 
         |-- 52 bits --| 

Теперь мы получаем 9 007 199 254 740 992 , и с числом, большим его, то, что формат может содержать, - это 2 раза от дроби , это означает, что теперь каждое 1 добавление в части дроби фактически равно 2 сложению, поэтому double 64-битный двоичный формат -precision не может содержать нечетные числа, если число больше 9 007 199 254 740 992 :

                            (consume 2^52 to move radix point to the end)
  1 . 0000 ---- 0001  *  2^53  =>  1  0000 ---- 0001.  *  2
     |-- 52 bits --|                 |-- 52 bits --|

Таким образом, когда число становится больше, чем 9 007 199 254 740 992 * 2 = 18 014 398 509 481 984, может быть проведено только 4 раза дроби :

input: 18014398509481984 + 1  output: 18014398509481984  // expected: 18014398509481985
input: 18014398509481984 + 2  output: 18014398509481984  // expected: 18014398509481986
input: 18014398509481984 + 3  output: 18014398509481984  // expected: 18014398509481987
input: 18014398509481984 + 4  output: 18014398509481988  // expected: 18014398509481988

Как насчет числа между [ 2 251 799 813 685 248 , 4 503 599 627 370 496 )?

 1 . 0000 ---- 0001  *  2^51  =>  1 0000 ---- 000.1
     |-- 52 bits --|                |-- 52 bits  --|

Битовое значение 1 после радикальной точки равно 2 ^ -1. (= 1/2, = 0,5) Таким образом, когда число меньше 4 503 599 627 370 496 (2 ^ 52), есть один бит, доступный для представления 1/2 раз целого числа :

input: 4503599627370495.5   output: 4503599627370495.5  
input: 4503599627370495.75  output: 4503599627370495.5  

Менее 2 251 799 813 685 248 (2 ^ 51)

input: 2251799813685246.75   output: 2251799813685246.8  // expected: 2251799813685246.75 
input: 2251799813685246.25   output: 2251799813685246.2  // expected: 2251799813685246.25 
input: 2251799813685246.5    output: 2251799813685246.5

// If the digits exceed 17, JavaScript round it to print it.
//, but the value is held correctly:

input: 2251799813685246.25.toString(2) 
output: "111111111111111111111111111111111111111111111111110.01"
input: 2251799813685246.75.toString(2) 
output: "111111111111111111111111111111111111111111111111110.11"
input: 2251799813685246.78.toString(2)   
output: "111111111111111111111111111111111111111111111111110.11"

И каков доступный диапазон экспонентной части ? формат выделяет для него 11 битов. Полный формат из Wiki : (для более подробной информации, пожалуйста, перейдите туда)

IEEE 754 Double Floating Point Format.svg

введите описание изображения здесь

Таким образом, чтобы сделать экспоненту 2 ^ 52, нам точно нужно установить e = 1075.

Карр
источник
13

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

for (var x = 2; x + 1 !== x; x *= 2);
console.log(x);

Что дает мне 9007199254740992 менее чем за миллисекунду в Chrome 30.

Он проверит степени 2, чтобы определить, какой из них, когда «добавлен» 1, равен себе.

Philippe97
источник
Это может привести к сбою вашего приложения, подумал.
Sapphire_Brick
8

Все, что вы хотите использовать для побитовых операций, должно быть в диапазоне от 0x80000000 (-2147483648 или -2 ^ 31) до 0x7fffffff (2147483647 или 2 ^ 31 - 1).

Консоль скажет вам, что 0x80000000 равно +2147483648, но 0x80000000 & 0x80000000 равно -2147483648.

Scato
источник
6

Пытаться:

maxInt = -1 >>> 1

В Firefox 3.6 это 2 ^ 31 - 1.

Мартин Нац
источник
2
@danorton: я не уверен, что вы понимаете, что делаете. ^значит возведен во власть . В консоли javascript ^есть XOR , а не повышен до
kumarharsh
2
откройте консоль Chrome / Firefox. Введите 5 ^ 2. В двоичном коде 5 - это 1012, а 2 - это 010. Теперь, если вы побитируете их XOR, вы получите 5(101) ^ 2(010) = 7(111) ПРОЧИТАЙТЕ ЭТО, ЕСЛИ ВЫ ЗАМЕДЛЕНЫ То, что обсуждается здесь, Math.pow()не ^оператор
kumarharsh
3
Опять же, я совсем не растерялся. Я прокомментировал и понизил то, что написано . Если подразумевается Math.pow (), то это то, что должно быть написано. В ответе на вопрос о JavaScript неуместно использовать синтаксис другого языка. Еще более неуместно использовать синтаксис, действительный в JavaScript, но с интерпретацией в JavaScript, значение которой отличается от того, что предполагается.
Данортон
10
2 ^ 31 - это то, как один пишет в тридцать первой степени по-английски. Это не в блоке кода. Будете ли вы жаловаться на кого-то, использующего; в ответ, потому что это символ с другим значением в Javascript?
LMM
3
Несмотря на то, что нужно писать 2³¹, а не 2 ^ 31 в виде обычного текста, обычно это делается, потому что большинство раскладок клавиатуры не имеют этих символов по умолчанию. По крайней мере, у меня не было проблем с пониманием того, что подразумевалось под этим ответом.
Джок
6

На момент написания, JavaScript получает новый тип данных: BigInt. Это предложение TC39 на этапе 4, которое будет включено в EcmaScript 2020 . BigIntдоступно в Chrome 67+, FireFox 68+, Opera 54 и Node 10.4.0. Это происходит в Safari и др ... Он вводит числовые литералы с суффиксом "n" и допускает произвольную точность:

var a = 123456789012345678901012345678901n;

Конечно, точность все равно будет потеряна, когда такое число (возможно, непреднамеренно) приведено к типу данных числа.

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

Например, генерация числа с сотнями тысяч десятичных цифр займет заметную задержку перед завершением:

console.log(BigInt("1".padEnd(100000,"0")) + 1n)

... но это работает.

trincot
источник
4

Я провел простой тест с формулой X- (X + 1) = - 1, и наибольшее значение XI, которое можно получить для работы в Safari, Opera и Firefox (протестировано в OS X) - 9e15. Вот код, который я использовал для тестирования:

javascript: alert(9e15-(9e15+1));
Raynet
источник
1
Обратите внимание, что 9e15 = 2 ^ 53 (см. Ответ @ Джимми).
Клин
6
9e15 = 9000000000000000. 2 ^ 53 = 9007199254740992. Поэтому, чтобы быть педантичным, 9e15 только приблизительно равен 2 ^ 53 (с двумя значащими цифрами).
devios1
@chaiguy В 90000000000000001 значимая цифра. в `9007199254740992` есть 15 значимых цифр.
Ройи Намир
@RoyiNamir Не хочу приводить здесь бессмысленные аргументы, но 9000000000000000 имеет 16 значащих цифр. Если вы хотите только 1, это должно быть записано как 9x10 ^ 15.
devios1
1
@chaiguy Нет. 9000000000000000как есть - есть 1SF. где 90*10^14есть 2. ( sigfigscalculator.appspot.com ) & mathsfirst.massey.ac.nz/Algebra/Decimals/SigFig.htm (нижняя часть)
Рой Намир
3

Я пишу это так:

var max_int = 0x20000000000000;
var min_int = -0x20000000000000;
(max_int + 1) === 0x20000000000000;  //true
(max_int - 1) < 0x20000000000000;    //true

То же самое для int32

var max_int32 =  0x80000000;
var min_int32 = -0x80000000;
Джером
источник
3

Давайте перейдем к источникам

Описание

MAX_SAFE_INTEGERКонстанта имеет значение 9007199254740991(9.007.199.254.740.991 или ~ 9 квадрильонов). Причина этого числа заключается в том, что JavaScript использует числа в формате с плавающей запятой двойной точности, как указано в IEEE 754, и может безопасно представлять числа только между-(2^53 - 1) и 2^53 - 1.

Безопасный в этом контексте относится к способности точно представлять целые числа и правильно их сравнивать. Например, Number.MAX_SAFE_INTEGER + 1 === Number.MAX_SAFE_INTEGER + 2будет оцениваться как true, что математически неверно. Видеть Number.isSafeInteger () для получения дополнительной информации.

Поскольку MAX_SAFE_INTEGERстатическое свойство Number , Вы всегда используете его как Number.MAX_SAFE_INTEGER, а не как свойство Number созданного вами объекта .

Совместимость браузера

введите описание изображения здесь

simhumileco
источник
-1

Scato wrotes:

все, что вы хотите использовать для побитовых операций, должно быть между 0x80000000 (-2147483648 или -2 ^ 31) и 0x7fffffff (2147483647 или 2 ^ 31 - 1).

консоль скажет вам, что 0x80000000 равно +2147483648, но 0x80000000 & 0x80000000 равно -2147483648

Шестнадцатеричные десятичные числа являются положительными значениями без знака, поэтому 0x80000000 = 2147483648 - это математически правильно. Если вы хотите сделать его значением со знаком, вам нужно сдвинуть вправо: 0x80000000 >> 0 = -2147483648. Вы также можете написать 1 << 31.

SammieFox
источник
-7

У Firefox 3, похоже, нет проблем с огромными числами.

1e + 200 * 1e + 100 - штраф до 1e + 300.

У Safari, похоже, нет проблем с этим. (Для справки, это на Mac, если кто-то еще решит проверить это.)

Если я не потерял свой мозг в это время дня, это намного больше, чем 64-разрядное целое число.

Jishi
источник
18
это не 64-битное целое число, это 64-битное число с плавающей запятой, из которых 52/53 бит составляют целочисленную часть. поэтому он будет обрабатывать до 1е300, но не с точной точностью.
Джимми
4
Джимми прав. Попробуйте это в своем браузере или командной строке JS:100000000000000010 - 1 => 100000000000000020
Райан
-7

Node.js и Google Chrome, похоже, используют 1024-битные значения с плавающей запятой, поэтому:

Number.MAX_VALUE = 1.7976931348623157e+308
TinyTimZamboni
источник
1
-1: максимальное представимое (не точное целое) число может быть ~ 2 ^ 1024, но это не означает, что они отклоняются от 64- битного стандарта IEEE-754 .
Рой Тинкер
2
MAX_INT? Вы имеете в виду MAX_VALUE?
Рауль Гуйу
3
это максимум значения с плавающей запятой . Это не значит, что вы можете хранить int так долго
phuclv
1
Или, более того, вы не можете надежно хранить int без потери точности . 2^53упоминается как MAX_SAFE_INTпотому, что выше этой точки значения становятся приближениями, так же, как и дроби.
IMSoP