Java tương đương với dài dài không dấu?


106

Trong C ++, tôi rất thích có quyền truy cập vào một số nguyên 64 bit không dấu, qua unsigned long long inthoặc qua uint64_t. Bây giờ, độ dài trong Java là 64 bit, tôi biết. Tuy nhiên, chúng đã được ký kết.

Có một long (dài) không dấu có sẵn dưới dạng nguyên thủy Java không? Làm thế nào để tôi sử dụng nó?


4
LƯU Ý Câu trả lời được chấp nhận đã lỗi thời từ Java 8 trở lên. Xem Câu trả lời của GigaStore để biết tính năng mới nơi bạn có thể yêu cầu Java coi một số là chưa có dấu. Không phải để sử dụng hàng ngày, nhưng tiện dụng khi bạn cần.
Basil Bourque

Câu trả lời:


55

Tôi không tin như vậy. Một khi bạn muốn phát triển lớn hơn thời hạn đã ký, tôi nghĩ BigInteger là cách duy nhất (không có lợi) để đi.


17
Câu trả lời này hơi lỗi thời (nó đã được đăng vào năm 2009). Bắt đầu từ Java 8 (phát hành tháng 3 năm 2014), có hỗ trợ cho dài chưa ký. Kiểm tra một ví dụ tôi đã đăng dưới đây như một câu trả lời.
Sáng

140

Khởi động Java 8, có hỗ trợ cho dài không dấu (64 bit không dấu). Cách bạn có thể sử dụng nó là:

Long l1 = Long.parseUnsignedLong("17916881237904312345");

Để in nó, bạn không thể chỉ in l1 mà trước tiên bạn phải:

String l1Str = Long.toUnsignedString(l1)

Sau đó

System.out.println(l1Str);

@ j10, Long ul1 = Long.parseUnsignedLong(objScannerInstance.next("\\d+"));Không chính xác thanh lịch vì nó thiếu kiểm tra phạm vi, nhưng nó sẽ cho phép bạn lấy các đầu vào số dài mà nếu không có thể vượt quá phạm vi của một ký tự dài. (Tăng cường thêm tính thực tế là Scanner::next(...)cũng có thể chấp nhận hoặc là một đối tượng mẫu hoặc String pattern.)
Spencer D

nó là khó khăn.
Alex78191

12

Không, không có. Bạn sẽ phải sử dụng kiểu longdữ liệu nguyên thủy và giải quyết các vấn đề về độ ký hoặc sử dụng một lớp chẳng hạn BigInteger.


7

Không, không có. Các nhà thiết kế của Java được ghi nhận là họ không thích các int không dấu. Sử dụng BigInteger để thay thế. Xem câu hỏi này để biết chi tiết.


22
Tôi tôn trọng Gosling vì những gì anh ấy đã làm, nhưng tôi nghĩ rằng việc anh ấy bảo vệ không có int không dấu là một trong những lời bào chữa ngớ ngẩn nhất mà tôi từng nghe. :-) Chúng tôi có nhiều thứ khó hiểu hơn trong Java hơn là int không dấu ... :-)
Brian Knoblauch

1
Gosling tại JavaPolis 2007 đã đưa ra một ví dụ rằng nó không hoạt động một cách khó hiểu đối với các int không được ký. Josh Bloch chỉ ra rằng nó cũng không hoạt động đối với các int đã ký. Số nguyên có kích thước tùy ý ftw!
Tom Hawtin - tackline


2
@PP: Tôi không nghĩ rằng có thể xác định các quy tắc hợp lý cho phép tương tác tự do giữa các loại có dấu và không dấu khi ít nhất một trong số chúng có hành vi gói được xác định. Điều đó đã được nói, byte unsigned hay ngắn unsigned sẽ gây ra không rắc rối kể từ byte không tương tác với các loại khác anyway. Một vấn đề lớn hơn là có hành vi gói được xác định cho các loại được sử dụng để đại diện cho số , khác với việc có các loại gói riêng biệt cho những trường hợp hiếm hoi đó (như tính toán mã băm) khi hành vi gói thực sự hữu ích.
supercat

3
@PP: Tôi ước các nhà thiết kế ngôn ngữ sẽ nhận ra tầm quan trọng của việc phân biệt các số với các vòng đại số (kiểu "gói số nguyên" là gì). Bất kỳ số kích thước nào cũng phải chuyển đổi hoàn toàn thành bất kỳ kích thước vòng nào, nhưng các vòng chỉ nên chuyển đổi thành số thông qua hàm hoặc thông qua typecast rõ ràng thành số kích thước tương tự . Hành vi của C, nơi các kiểu không dấu thường hoạt động như các vành đại số nhưng đôi khi hoạt động như các số có lẽ là tồi tệ nhất trong tất cả các thế giới có thể có; Tôi không thể trách Gosling vì muốn tránh điều đó, mặc dù anh ta đã hoàn toàn sai cách tiếp cận khi làm như vậy.
supercat

6

Java 8 cung cấp một tập hợp các thao tác dài không dấu cho phép bạn trực tiếp coi các biến Dài đó là Long không dấu, sau đây là một số biến thường được sử dụng:

Và các phép cộng, trừ và nhân giống nhau đối với các long có dấu và không dấu.


2
Xem nhanh mã nguồn cho tôi biết phải thận trọng một chút với các phương pháp này. Khi độ dài thực sự là số âm (tức là có sự khác biệt so với trường hợp đã ký) thì lớp BigInteger sẽ được sử dụng. Điều này có nghĩa là tối đa 8 BigIntegers mới sẽ được phân bổ, con số này khá nhiều và chắc chắn là một sự sụt giảm hiệu suất.
Toonijn 24/09/2016

4

Tùy thuộc vào các thao tác bạn định thực hiện, kết quả là giống nhau, có dấu hoặc không dấu. Tuy nhiên, trừ khi bạn đang sử dụng các thao tác tầm thường, bạn sẽ kết thúc bằng cách sử dụng BigInteger.


4

Trong thời gian dài chưa ký, bạn có thể sử dụng lớp UnsignedLong từ thư viện Guava :

Nó hỗ trợ các hoạt động khác nhau:

  • thêm
  • dấu trừ
  • lần
  • mod
  • chia

Điều dường như bị thiếu vào lúc này là các toán tử dịch chuyển byte. Nếu bạn cần những thứ đó, bạn có thể sử dụng BigInteger từ Java.


3

Java không có kiểu không dấu. Như đã đề cập, bao gồm chi phí của BigInteger hoặc sử dụng JNI để truy cập mã gốc.


15
char là một giá trị 16-bit không dấu;)
Peter Lawrey

2

Gói org.apache.axis.types có một

Lớp học UnsignedLong.

cho maven:

<dependency>
    <groupId>org.apache.axis</groupId>
    <artifactId>axis</artifactId>
    <version>1.4</version>
</dependency>

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.