int () truncates its result to 32 bits

Đang mở Phù hợp với người mới
#911 2 bình luận 0 reaction 0 người được giao Xem trên GitHub

Chưa có ai nhận issue này.

Đánh giá

Độ khó
2/5
Thời gian dự kiến
1-3 giờ
Mức phù hợp với người mới
88/100
Loại issue
Lỗi
Độ rõ ràng
Đặc tả rõ ràng
Mức độ hoạt động
Sôi nổi
Công nghệ
javascript, python
Lĩnh vực
compilers

Hướng nghiên cứu

Bắt đầu tại dòng 291 của builtin.js, nơi int() hiện đang sử dụng phép chuyển đổi bitwise của JavaScript, và xem xét development/automated_tests/transcrypt/div_issues/init.py để tìm testlet của Issue 911. Làm cho các kiểm tra số nguyên lớn vượt qua, đồng thời giữ nguyên việc cắt ngắn về 0 đối với các số float âm, sau đó chạy testlet bằng Node với các tùy chọn trình biên dịch đã nêu.

Do mô hình lập chỉ mục viết ra từ nội dung của issue.

Mô tả

int (x) compiles to float (x) | 0. JavaScript's | converts its left operand with ToInt32, so the result is always a signed 32 bit integer. Arguments outside -2**31 ... 2**31 - 1 come back wrong, multiples of 2**32 come back as 0.

Reproducer

values = [8589934588, 9007199254740988, 2147483648, 4294967296]
for v in values:
    print (v, '->', int (v))

CPython:

8589934588 -> 8589934588
9007199254740988 -> 9007199254740988
2147483648 -> 2147483648
4294967296 -> 4294967296

Transcrypt:

8589934588 -> -4
9007199254740988 -> -4
2147483648 -> -2147483648
4294967296 -> 0

Run with 3.7.16 on Python 3.7, compiled with -b -n -e 6 and executed under
node. Line 291 of __builtin__.js is identical on current master.

The failure is quiet. A memory size in kB, a file offset or a timestamp in microseconds passes 2**31 during normal operation and then yields a small or negative number instead of an error.

Testlet

For development/automated_tests/transcrypt/div_issues/__init__.py:

    autoTester.check ('Issue 911')  # int () truncated to 32 bits
    autoTester.check (int (2147483648))
    autoTester.check (int (4294967296))
    autoTester.check (int (8589934588))
    autoTester.check (int (9007199254740988))
    autoTester.check (int (-5.7), int (5.7))

Possible fix

export function int (any) {
    var f = float (any);
    return f === Infinity || f === -Infinity || isNaN (f) ? 0 : Math.trunc (f);
};

This makes int () exact over the whole range where a JavaScript number is exact, up to 2**53 - 1, and leaves truncation toward zero for negative floats unchanged. With the patch applied the reproducer above matches CPython.

Math.trunc is ES6. The default target is esv 6 and javascriptVersion gates nothing in the code generator, so no version switch is needed. int has no callers inside the runtime.

Note on NaN and Infinity

NaN | 0 and Infinity | 0 currently yield 0, where CPython raises ValueError and OverflowError. The version above keeps the 0 to stay minimal. Raising instead would match CPython but changes behaviour beyond the range fix, so it seems worth deciding separately.

Ngôn ngữ chính
Python
Star
2.9k
Fork
218
Chỉ số merge pull request
Không có pull request nào được merge trong 30 ngày

Hướng dẫn đóng góp

Chưa lập chỉ mục được hướng dẫn đóng góp cho kho mã nguồn này

Bắt đầu từ đâu

  1. Đọc hết issue, rồi đọc hướng dẫn đóng góp của dự án.
  2. Bình luận trên issue rằng bạn sẽ nhận — tránh hai người làm cùng một việc.
  3. Fork repository và làm thay đổi trên một nhánh.
  4. Mở pull request có tham chiếu số hiệu của issue.

Issue khác của TranscryptOrg/Transcrypt

Tất cả issue của TranscryptOrg/Transcrypt

Issue tương tự

Thêm issue về Python

Nhận issue mới trong hộp thư của bạn

Bản tóm tắt ngắn những issue GitHub phù hợp với người mới.