जावा में एक अहस्ताक्षरित int की घोषणा


316

क्या जावा में एक अहस्ताक्षरित int घोषित करने का कोई तरीका है?

या प्रश्न को इस तरह भी तैयार किया जा सकता है: जावा अहस्ताक्षरित के बराबर क्या है?

बस आपको वह संदर्भ बताना है जिसे मैं जावा के कार्यान्वयन पर देख रहा था String.hashcode()। मैं टक्कर की संभावना का परीक्षण करना चाहता था यदि पूर्णांक 32 अहस्ताक्षरित int थे।


7
जावा में कोई अहस्ताक्षरित प्रकार नहीं हैं।
एंड्रयू लोगविनोव

1
यह पोस्ट आपकी मदद कर सकता है stackoverflow.com/a/4449161/778687
tusar

2
एक तरह से AFAICT प्रतीत नहीं होता है। संबंधित: stackoverflow.com/questions/430346/…
जेम्स मैनिंग

11
यह उस उद्देश्य पर निर्भर करता है जिसे आप प्राप्त करने की कोशिश कर रहे हैं। अधिकांश उद्देश्यों के लिए, जावा में सभी पूर्णांकों पर हस्ताक्षर किए गए हैं। हालांकि, अगर आप कर सकते हैं का इलाज एक हस्ताक्षरित पूर्णांक के रूप में एक विशिष्ट मामले में अहस्ताक्षरित: आप सही संकेत का उपयोग करके विस्तार के बिना बदल सकते हैं >>>बजाय ऑपरेटर >>
dasblinkenlight

जवाबों:


310

जावा में अहस्ताक्षरित पूर्णांकों के लिए डेटाटाइप नहीं है ।

यदि आपको बड़े मान संग्रहीत करने की आवश्यकता है long, intतो आप इसके बजाय परिभाषित कर सकते हैं ।

आप किसी हस्ताक्षरित पूर्णांक का भी उपयोग कर सकते हैं जैसे कि यह अहस्ताक्षरित था। दो के पूरक प्रतिनिधित्व का लाभ यह है कि हस्ताक्षर और अहस्ताक्षरित पूर्णांक के लिए बाइनरी स्तर पर अधिकांश ऑपरेशन (जैसे इसके अलावा, घटाव, गुणा, और बाईं पारी) समान हैं। कुछ ऑपरेशन (विभाजन, सही बदलाव, तुलना और कास्टिंग), हालांकि, अलग-अलग हैं। जावा एसई 8 के रूप में, Integerकक्षा में नए तरीके आपको अहस्ताक्षरित अंकगणित करने के लिएint डेटा प्रकार का पूरी तरह से उपयोग करने की अनुमति देते हैं :

जावा एसई 8 और बाद में, आप एक अहस्ताक्षरित 32-बिट पूर्णांक का प्रतिनिधित्व करने के लिए अंतर डेटा प्रकार का उपयोग कर सकते हैं, जिसका न्यूनतम मान 0 और अधिकतम मान 2 ^ 32-1 है। अहस्ताक्षरित पूर्णांक के रूप में int डेटा प्रकार का उपयोग करने के लिए Integer वर्ग का उपयोग करें। की तरह स्टेटिक तरीकों compareUnsigned, divideUnsignedआदि अहस्ताक्षरित पूर्णांकों के लिए अंकगणितीय आपरेशनों का समर्थन करने के पूर्णांक वर्ग के लिए जोड़ा गया है।

ध्यान दें कि intघोषित किए जाने के बाद भी चर पर हस्ताक्षर किए जाते हैं लेकिन Integerकक्षा में उन विधियों का उपयोग करके अब बिना अंकगणित संभव है ।


11
निष्पक्ष होने के लिए, कई परियोजनाओं के लिए तकनीकी आवश्यकताएं इतनी सख्त नहीं होती हैं और आप वास्तव में इस तरह की स्मृति को "बेकार" कर सकते हैं।
शिमोन विज़सर

6
मुझे पता है, मैं जावा के मूल उद्देश्य को भी समझता हूं। लेकिन उदाहरण के लिए स्मार्टफोन अतिरिक्त मेमोरी के साथ डिस्पोज नहीं करते हैं। और वे आमतौर पर जावा का उपयोग करते हैं, जहां तक ​​मुझे पता है। लेकिन ठीक है, मैं जावा प्रोग्रामर और अन्य लोगों के बीच युद्ध शुरू नहीं करना चाहता।
टॉम ज़ातो - मोनिका

122
मेरे लिए यह सिर्फ पैसे बर्बाद करने का मामला नहीं है। जब आप एक सा स्तर पर काम करते हैं, तो अहस्ताक्षरित के साथ काम करना आसान होता है
क्रंचर

24
जावा 8 के रूप में, यह अब सच नहीं है । जावा एसई 8 और बाद में, आप intएक अहस्ताक्षरित 32-बिट पूर्णांक का प्रतिनिधित्व करने के लिए डेटा प्रकार का उपयोग कर सकते हैं , जिसका न्यूनतम मूल्य 0और अधिकतम मूल्य है 2^32-1। - docs.oracle.com/javase/tutorial/java/nutsandbolts/… और docs.oracle.com/javase/8/docs/api/java/lang/Integer.html
8

2
@ 7SpecialGems: मैंने उस जानकारी को शामिल करने के लिए उत्तर अपडेट कर दिया है। कहा जा रहा है कि, अहस्ताक्षरित पूर्णांक घोषित करना या नकारात्मक मूल्यों को बाहर करना संभव नहीं है, यह केवल तभी संभव है intजब यह विभिन्न तरीकों का उपयोग करके अहस्ताक्षरित हो।
शिमोन विसेर

70

1
@stas मुझे अहस्ताक्षरित डेटाटेस का उपयोग करने की क्षमता होने पर उपयोग और बड़े सौदे को समझने में कठिनाई हो रही है। ऑनलाइन पढ़े गए विभिन्न स्रोतों से, ऐसा लगता है जैसे यह अधिकतम मूल्य को चौड़ा करने के चारों ओर घूमता है, और प्रकृति द्वारा निहित यह गारंटी देता है कि यह एक सकारात्मक संख्या है। क्या मेरी समझ सही है, या अन्य प्रमुख कारण हैं? इसके अलावा, अब जब Integerजावा 8 में वर्ग किसी को अहस्ताक्षरित int का उपयोग करने की अनुमति देता है, तो क्या अंतरिक्ष और गति के बीच का अंतर है (क्योंकि C / C ++ में वे आदिम हैं, जबकि जावा में, यह पूरी वस्तु आवरण है)
अब्दुल

2
@ अब्दुल - जब आप बिट स्तर पर काम करते हैं (आमतौर पर क्योंकि आप हार्डवेयर के साथ हस्तक्षेप कर रहे होते हैं) तो आपको एक निश्चित तरीके से व्यवहार करने के लिए मूल्यों की आवश्यकता होती है। यानी - 11111111 से लेकर 00000000 तक रोल ओवर करने के बाद बिना हस्ताक्षर के स्थान पर हस्ताक्षर किए गए सीआरसी गणनाओं को तोड़ सकते हैं आदि यह शो स्टॉपर नहीं है, बस समय बर्बाद किया है।
लोर्न के

3
@ लोर्न के: जावा में, intरोल ओवर, भले ही वे हस्ताक्षर किए गए हों। यह C / C ++ है जहां अहस्ताक्षरित रोल खत्म हो गए हैं, लेकिन ओवरफ्लो पर "अपरिभाषित व्यवहार" पर हस्ताक्षर किए गए कारण। यदि "रोलिंग ओवर" आपकी एकमात्र चिंता है, तो आपको अहस्ताक्षरित होने की आवश्यकता नहीं है। मुझे लगता है, यही कारण है कि सीआरसी दिनचर्या आदि जावा में अतिरिक्त प्रयासों के बिना काम करते हैं। और यही कारण है कि नया एपीआई केवल पार्सिंग, स्वरूपण, तुलना, विभाजन और शेष जोड़ता है। अन्य सभी ऑपरेशन, अर्थात् सभी बिट जोड़तोड़, लेकिन इसके अलावा, घटाव, गुणा, आदि भी सही काम कर रहे हैं।
होल्गर

4
@Ciprian Tomoiaga: रोलओवर के साथ जोड़ने के लिए, इनपुट के बिट पैटर्न और परिणाम इस बात पर निर्भर नहीं करते हैं कि आप इसे हस्ताक्षरित संख्या या अहस्ताक्षरित संख्या के रूप में व्याख्या करते हैं। यदि आपके पास धैर्य है, तो आप इसे सभी 2
होल्गर

3
@Holger स्पष्टीकरण के लिए धन्यवाद! वास्तव में, यह पता चला है कि हम वास्तव में 2 के पूरक का उपयोग क्यों करते हैं। मैंने इसे कुछ 2 ^ 8 संयोजनों के साथ
आज़माया था

66

क्या किसी इंट में मान हस्ताक्षरित है या अहस्ताक्षरित है, इस पर निर्भर करता है कि बिट्स की व्याख्या कैसे की जाती है - जावा एक हस्ताक्षरित मूल्य के रूप में बिट्स की व्याख्या करता है (इसमें अहस्ताक्षरित आदिम नहीं है)।

यदि आपके पास एक ऐसा इरादा है जिसे आप एक अहस्ताक्षरित मान के रूप में व्याख्या करना चाहते हैं (जैसे आप एक DataInputStream से एक int पढ़ते हैं जिसे आप जानते हैं कि इसमें एक अहस्ताक्षरित मान है) तो आप निम्न चाल कर सकते हैं।

int fourBytesIJustRead = someObject.getInt();
long unsignedValue = fourBytesIJustRead & 0xffffffffl;

ध्यान दें, यह महत्वपूर्ण है कि हेक्स शाब्दिक एक लंबा शाब्दिक है, न कि एक आंतरिक शाब्दिक - इसलिए अंत में 'एल'।


3
मेरे लिए यह सबसे अच्छा उत्तर है ... मेरा डेटा एक एनएफसी कार्ड यूआईडी से आता है, जिसमें 4 या 8 बाइट्स हो सकते हैं ... 4 बाइट्स के मामले में मुझे इसे एक अनिर्दिष्ट इंट में डालने की आवश्यकता थी, और मैं नहीं कर सका। ByteBuffer.getLong का उपयोग करें क्योंकि यह 64-बिट डेटा नहीं था। धन्यवाद।
लाउडेनवियर

इसे लंबा होने की आवश्यकता क्यों है। क्या आप अभी नहीं कर सकते हैं 0xFFFFFFऔर इंट रख सकते हैं?
14

19

हम मॉडल करने के लिए अहस्ताक्षरित संख्या जरूरत MySQL के अहस्ताक्षरित TINYINT, SMALLINT, INT, BIGINTमें jOOQ , जिसके कारण हम बनाया है jOOU , जावा में अहस्ताक्षरित पूर्णांक संख्या के लिए प्रकार आवरण एक minimalistic पुस्तकालय की पेशकश। उदाहरण:

import static org.joou.Unsigned.*;

// and then...
UByte    b = ubyte(1);
UShort   s = ushort(1);
UInteger i = uint(1);
ULong    l = ulong(1);

ये सभी प्रकार विस्तारित होते हैं java.lang.Numberऔर इन्हें उच्च-क्रम वाले आदिम प्रकारों में परिवर्तित किया जा सकता है BigInteger। उम्मीद है की यह मदद करेगा।

(अस्वीकरण: मैं इन पुस्तकालयों के पीछे कंपनी के लिए काम करता हूं)


यह बहुत सुविधाजनक लगता है! उल्लेख करने के लिए धन्यवाद। :)
लुकास सूसा

7

अहस्ताक्षरित संख्या के लिए आप इन कक्षाओं का उपयोग अमरूद पुस्तकालय से कर सकते हैं :

वे विभिन्न अभियानों का समर्थन करते हैं:

  • प्लस
  • ऋण
  • बार
  • आधुनिक
  • द्वारा विभाजित

फिलहाल जो चीज गायब लगती है वो है बाइट शिफ्ट ऑपरेटर्स। अगर आपको जरूरत है तो आप जावा से बिगइन्टेगर का उपयोग कर सकते हैं।


4

char16 बिट अहस्ताक्षरित पूर्णांकों के लिए उपयोग करें ।


चार 32bit अहस्ताक्षरित int नहीं हैं, लेकिन char स्मृति लाभ के लिए एक अच्छा जवाब है। यह लिंक: stackoverflow.com/questions/1841461/unsigned-short-in-java (ऊपर दिए गए jqr से)
blobmaster

2

शायद यही आपका मतलब था?

long getUnsigned(int signed) {
    return signed >= 0 ? signed : 2 * (long) Integer.MAX_VALUE + 2 + signed;
}
  • getUnsigned(0) → 0
  • getUnsigned(1) → 1
  • getUnsigned(Integer.MAX_VALUE) → 2147483647
  • getUnsigned(Integer.MIN_VALUE) → 2147483648
  • getUnsigned(Integer.MIN_VALUE + 1) → 2147483649

यदि आप बयानों के बजाय टर्नरी ऑपरेटरों के साथ आलसी टाइपिंग के लिए प्रदर्शन समय के एक सेकंड का बलिदान कर रहे हैं। अच्छा नही। (मजाक कर रहे)
ytpillai

5
क्या आप वास्तव में सोचते हैं, 2 * (long) Integer.MAX_VALUE + 2समझने में आसान है 0x1_0000_0000L? इस संबंध में, बस क्यों नहीं return signed & 0xFFFF_FFFFL;?
होल्गर

2

ऐसा लगता है कि आप उन्हें उपयोग करने से पहले "तार्किक और" मूल्यों पर हस्ताक्षर करके समस्या को संभाल सकते हैं:

उदाहरण (का मूल्य byte[] header[0]है 0x86):

System.out.println("Integer "+(int)header[0]+" = "+((int)header[0]&0xff));

परिणाम:

Integer -122 = 134

2

यहाँ अच्छे उत्तर हैं, लेकिन मुझे बिटवाइज़ ऑपरेशंस का कोई प्रदर्शन नहीं दिखता है। विज़र की तरह (वर्तमान में स्वीकृत उत्तर) कहता है, जावा डिफ़ॉल्ट रूप से पूर्णांक पर हस्ताक्षर करता है (जावा 8 में पूर्णांक नहीं दिया गया है, लेकिन मैंने कभी भी इसका उपयोग नहीं किया है)। आगे की हलचल के बिना, चलो यह करते हैं ...

RFC 868 उदाहरण

यदि आपको IO को अहस्ताक्षरित पूर्णांक लिखने की आवश्यकता है तो क्या होगा? व्यावहारिक उदाहरण वह है जब आप RFC 868 के अनुसार समय का उत्पादन करना चाहते हैं । इसके लिए एक 32-बिट, बिग-एंडियन, अहस्ताक्षरित पूर्णांक की आवश्यकता होती है जो 12:00 AM 1 जनवरी, 1900 के बाद से सेकंड की संख्या को एन्कोड करता है। आप इसे कैसे एनकोड करेंगे?

इस तरह अपना स्वयं का अहस्ताक्षरित 32-बिट पूर्णांक बनाएं:

4 बाइट्स (32 बिट) की बाइट सरणी घोषित करें

Byte my32BitUnsignedInteger[] = new Byte[4] // represents the time (s)

यह सरणी को इनिशियलाइज़ करता है, देखते हैं कि क्या बाइट एरेज़ जावा में शून्य से शुरू होती है? । अब आपको प्रत्येक बाइट को बड़े-एंडियन ऑर्डर में जानकारी के साथ भरना होगा (या यदि आप कहर बरपाना चाहते हैं तो थोड़ा-सा एंडियन)। यह मानते हुए कि आपके पास एक लंबा समय है (लंबे पूर्णांक जावा में 64 बिट लंबे हैं) कहा जाता है secondsSince1900(जो केवल पहले 32 बिट्स का उपयोग करता है, और आपने इस तथ्य को संभाला है कि दिनांक 12:00 पूर्वाह्न 1 जनवरी, 1970), तब आप इसे से बिट्स निकालने के लिए तार्किक और का उपयोग कर सकते हैं और उन बिट्स को पदों (अंकों) में शिफ्ट कर सकते हैं जिन्हें बाइट में ले जाने पर और बड़े-एंडियन ऑर्डर में नजरअंदाज नहीं किया जाएगा।

my32BitUnsignedInteger[0] = (byte) ((secondsSince1900 & 0x00000000FF000000L) >> 24); // first byte of array contains highest significant bits, then shift these extracted FF bits to first two positions in preparation for coersion to Byte (which only adopts the first 8 bits)
my32BitUnsignedInteger[1] = (byte) ((secondsSince1900 & 0x0000000000FF0000L) >> 16);
my32BitUnsignedInteger[2] = (byte) ((secondsSince1900 & 0x000000000000FF00L) >> 8);
my32BitUnsignedInteger[3] = (byte) ((secondsSince1900 & 0x00000000000000FFL); // no shift needed

हमारा my32BitUnsignedIntegerअब एक अहस्ताक्षरित 32-बिट, बिग-एंडियन पूर्णांक के बराबर है जो RCF 868 मानक का पालन करता है। हां, लंबे डेटाटाइप पर हस्ताक्षर किए गए हैं, लेकिन हमने उस तथ्य को नजरअंदाज कर दिया है, क्योंकि हमने माना कि सेकंडसिंस 1900 ने केवल निचले 32 बिट्स का उपयोग किया है)। एक बाइट में लंबे समय तक बैठने के कारण, 2 ^ 7 (हेक्स में पहले दो अंक) से अधिक सभी बिट्स को नजरअंदाज कर दिया जाएगा।

स्रोत संदर्भित: जावा नेटवर्क प्रोग्रामिंग, 4 संस्करण।


1

बस इस कोड को बनाया, जो कि "this.altura" को ऋणात्मक से धनात्मक संख्या में परिवर्तित करता है। उम्मीद है कि यह किसी की जरूरत में मदद करता है

       if(this.altura < 0){    

                        String aux = Integer.toString(this.altura);
                        char aux2[] = aux.toCharArray();
                        aux = "";
                        for(int con = 1; con < aux2.length; con++){
                            aux += aux2[con];
                        }
                        this.altura = Integer.parseInt(aux);
                        System.out.println("New Value: " + this.altura);
                    }

-19

आप Math.abs (संख्या) फ़ंक्शन का उपयोग कर सकते हैं। यह एक सकारात्मक संख्या देता है।


12
नाइटपिक: यदि आप पास नहीं हैंMIN_VALUE
डेनिस मेंग

2
@ kyo722 मैं कल्पना नहीं कर सकता कि यह अहस्ताक्षरित प्राइमेट की श्रेणी में एक सकारात्मक मूल्य लौटाएगा।
फ्लोरियन आर। क्लेन

1
नाइटपिक # 2: यदि आप पास नहीं करते हैं0
21
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.