วิธีการเปรียบเทียบจำนวนเต็มสองตัวใน Java อย่างถูกต้องเป็นอย่างไร


217

ฉันรู้ว่าถ้าคุณเปรียบเทียบจำนวนเต็มดั้งเดิมของกล่องกับค่าคงที่เช่น:

Integer a = 4;
if (a < 5)

a จะถูกเลิกทำโดยอัตโนมัติและการเปรียบเทียบจะใช้งานได้

อย่างไรก็ตามจะเกิดอะไรขึ้นเมื่อคุณเปรียบเทียบสองกล่องIntegersและต้องการเปรียบเทียบความเท่าเทียมกันหรือน้อยกว่า / มากกว่า

Integer a = 4;
Integer b = 5;

if (a == b)

โค้ดด้านบนจะส่งผลให้มีการตรวจสอบเพื่อดูว่าพวกเขาเป็นวัตถุเดียวกันหรือไม่หรือจะกล่องอัตโนมัติในกรณีนั้น?

เกี่ยวกับ:

Integer a = 4;
Integer b = 5;

if (a < b)

?


16
เกิดอะไรขึ้นเมื่อคุณลองทำ คุณสังเกตอะไร
บาร์ต Kiers

31
@Bart Kiers: การทดสอบอย่างชัดเจนสามารถพิสูจน์หักล้างได้ไม่พิสูจน์ว่าเกิดการแกะกล่อง หากใช้==แทนการequalsให้ผลลัพธ์ที่ถูกต้องนั่นอาจเป็นเพราะหมายเลขที่บรรจุอยู่ในกล่องกำลังถูกใช้งานหรือนำกลับมาใช้ใหม่ เหตุผลที่ถามคำถามนี้คือเพื่อค้นหาสิ่งที่เกิดขึ้นภายในไม่ใช่สิ่งที่ดูเหมือนจะเกิดขึ้น (อย่างน้อยนั่นคือเหตุผลที่ฉันมาที่นี่)
จิม Pivarski

เกิดอะไรขึ้นกับบัญชีของคุณ

คำตอบ:


303

ไม่ == ระหว่างจำนวนเต็มยาว ฯลฯ จะตรวจสอบความเท่าเทียมกันของการอ้างอิง - เช่น

Integer x = ...;
Integer y = ...;

System.out.println(x == y);

สิ่งนี้จะตรวจสอบว่าxและyอ้างถึงวัตถุเดียวกันมากกว่าวัตถุเท่ากันหรือไม่

ดังนั้น

Integer x = new Integer(10);
Integer y = new Integer(10);

System.out.println(x == y);

falseรับประกันได้ว่าจะพิมพ์ การใช้ค่าออโต้บ็อกซ์ "เล็ก" ระหว่างประเทศอาจทำให้ได้ผลลัพธ์ที่ยุ่งยาก:

Integer x = 10;
Integer y = 10;

System.out.println(x == y);

สิ่งนี้จะพิมพ์trueเนื่องจากกฎของมวย ( JLS หัวข้อ 5.1.7 ) ยังคงใช้ความเท่าเทียมกันของการอ้างอิง แต่การอ้างอิงที่แท้จริงมีค่าเท่ากัน

หากค่า p ที่ถูกบรรจุอยู่เป็นตัวอักษรจำนวนเต็มของ type int ระหว่าง -128 ถึง 127 ที่รวม (§3.10.1) หรือบูลีนตัวอักษรที่แท้จริงหรือเท็จ (§3.10.3) หรือตัวอักษรตัวอักษรระหว่าง '\ u0000' และ รวม '\ u007f' (§3.10.4) จากนั้นให้ a และ b เป็นผลลัพธ์ของการแปลงมวยสองอันของ p เป็นกรณีที่ a == b เสมอ

โดยส่วนตัวฉันจะใช้:

if (x.intValue() == y.intValue())

หรือ

if (x.equals(y))

ตามที่คุณพูดสำหรับการเปรียบเทียบระหว่างประเภท wrapper ( Integer, Longฯลฯ ) และชนิดตัวเลข ( int, longฯลฯ ) ค่าชนิดของ wrapper จะไม่ถูกทำกล่องและการทดสอบจะใช้กับค่าดั้งเดิมที่เกี่ยวข้อง

สิ่งนี้เกิดขึ้นเป็นส่วนหนึ่งของการเลื่อนระดับตัวเลขไบนารี ( JLS ส่วน 5.6.2 ) ดูเอกสารประกอบการของแต่ละบุคคลเพื่อดูว่ามีการนำไปใช้หรือไม่ ตัวอย่างเช่นจากเอกสารสำหรับ==และ!=( JLS 15.21.1 ):

หากโอเปอแรนด์ของโอเปอเรเตอร์ความเท่ากันเป็นทั้งชนิดตัวเลขหรือชนิดหนึ่งเป็นประเภทตัวเลขและอีกประเภทหนึ่งสามารถแปลงสภาพได้ (§5.1.8) เป็นประเภทตัวเลข

และสำหรับ<, <=, >และ>=( JLS 15.20.1 )

ประเภทของตัวถูกดำเนินการของตัวดำเนินการเปรียบเทียบเชิงตัวเลขแต่ละประเภทจะต้องเป็นประเภทที่สามารถแปลงได้ (§5.1.8) เป็นชนิดตัวเลขดั้งเดิมหรือเกิดข้อผิดพลาดในการรวบรวมเวลา การเลื่อนระดับเป็นเลขฐานสองจะดำเนินการกับตัวถูกดำเนินการ (§5.6.2) หากประเภทตัวถูกเลื่อนขั้นของตัวถูกดำเนินการนั้นเป็นแบบ int หรือแบบยาวการเปรียบเทียบจำนวนเต็มจะถูกดำเนินการ หากประเภทที่ได้รับการเลื่อนขั้นนี้เป็นแบบลอยหรือสองเท่าจะทำการเปรียบเทียบจุดลอย

โปรดสังเกตว่าสิ่งเหล่านี้ไม่ได้รับการพิจารณาว่าเป็นส่วนหนึ่งของสถานการณ์ที่ไม่มีประเภทใดเป็นประเภทตัวเลข


2
มีเหตุผลใดที่เราอยากเขียนx.compareTo(y) < 0แทนที่จะเป็นx < y?
Max Nanasy

1
@ MaxNanasy: ไม่ใช่ว่าฉันจะนึกได้ทันที
Jon Skeet

2
ในฐานะของ Java 1.6.27+ มีการโอเวอร์โหลดที่เท่ากับในคลาส Integer ดังนั้นจึงควรมีประสิทธิภาพเท่ากับการเรียก. intValue () มันเปรียบเทียบค่าเป็น int ดั้งเดิม
otterslide

ดังที่ @otterslide กล่าวว่าสิ่งนี้ไม่จำเป็นใน Java 8 อีกต่อไป การเปรียบเทียบจำนวนเต็มกับจำนวนเต็มเป็นค่าเริ่มต้น
Axel Prieto

1
@Axel: การเพิ่มเกินพิกัดจะไม่เปลี่ยนพฤติกรรมของตัวดำเนินการ == แม้ว่าจะเป็นอย่างไร ฉันไม่ได้อยู่ในฐานะที่จะทำการทดสอบในตอนนี้ แต่ฉันจะประหลาดใจมากถ้าสิ่งนั้นเปลี่ยนไป
Jon Skeet

44

==จะยังคงทดสอบความเท่าเทียมกันของวัตถุ มันง่ายที่จะถูกหลอกอย่างไรก็ตาม:

Integer a = 10;
Integer b = 10;

System.out.println(a == b); //prints true

Integer c = new Integer(10);
Integer d = new Integer(10);

System.out.println(c == d); //prints false

ตัวอย่างของคุณที่มีความไม่เท่าเทียมกันจะทำงานได้เนื่องจากไม่ได้กำหนดไว้ในวัตถุ อย่างไรก็ตามด้วยการ==เปรียบเทียบความเท่าเทียมกันของวัตถุจะยังคงถูกตรวจสอบ ในกรณีนี้เมื่อคุณเริ่มต้นวัตถุจากกล่องดั้งเดิมจะใช้วัตถุเดียวกัน (ทั้ง a และ b) นี่เป็นการเพิ่มประสิทธิภาพที่ไม่เป็นไรเนื่องจากคลาสกล่องแบบดั้งเดิมจะไม่เปลี่ยน


ฉันคิดว่ามันคือการทดสอบความเท่าเทียมกันของวัตถุ ฉันมีผลลัพธ์แปลก ๆ ฉันควรแทนที่ด้วย. equals () หรือไม่ นอกจากนี้คุณรู้สึกว่าฉันควรปล่อยให้ความไม่เท่าเทียมกันในขณะที่พวกเขาเป็นหรือทำวิธีอื่นเช่นกัน?

มีบางกรณีที่ไม่เห็นได้ชัดที่มีการล็อคอัตโนมัติ ฉันได้ตั้งค่า IDE (Eclipse) เป็นสีอะไรก็ตามที่ไม่ได้ใส่กล่องสีแดงนี่ช่วยฉันจากข้อผิดพลาดในบางโอกาส หากคุณกำลังเปรียบเทียบจำนวนเต็มสองตัวให้ใช้. equals หากคุณต้องการทำให้ความไม่เท่าเทียมของคุณชัดเจนให้เขียน cast อย่างชัดเจน: ถ้า ((int) c <(int) d) ... ; นอกจากนี้คุณยังสามารถทำได้: c.compareTo (d) <0 // === c <d
Adam Lewis

12
และถ้าคุณเปลี่ยนตัวอักษรตัวเลขเป็น200แบบทดสอบทั้งสองจะพิมพ์ออกfalseมา
Daniel Earwicker

2
... สำหรับการปรับใช้ JVM ส่วนใหญ่นั่นคือ ตามข้อกำหนดของภาษาผลลัพธ์อาจแตกต่างกันระหว่างการนำไปใช้งาน
Daniel Earwicker

4
ฉันคิดว่ามันชัดเจนกว่าที่จะเรียกว่า "ความเท่าเทียมกันอ้างอิง" - วิธีนี้ชัดเจนว่าคุณหมายถึงอะไร ฉันมักจะเข้าใจ "ความเท่าเทียมกันของวัตถุ" เพื่อหมายถึง "ผลลัพธ์ของequalsการถูกเรียกว่า"
Jon Skeet

28

ตั้งแต่ Java 1.7 คุณสามารถใช้Objects.equals :

java.util.Objects.equals(oneInteger, anotherInteger);

ผลตอบแทนจริงถ้าอาร์กิวเมนต์มีค่าเท่ากันและเป็นเท็จอย่างอื่น ดังนั้นถ้าทั้งสองอาร์กิวเมนต์เป็นโมฆะจริงจะถูกส่งกลับและถ้าอาร์กิวเมนต์หนึ่งเป็นโมฆะจะส่งคืนเท็จ มิฉะนั้นความเท่าเทียมกันจะถูกกำหนดโดยใช้วิธีการเท่ากับของอาร์กิวเมนต์แรก


สิ่งนี้จัดการ nulls ดังนั้นทำให้ง่าย ขอบคุณ!
Darren Parker

10

== ตรวจสอบความเท่าเทียมกันอ้างอิง แต่เมื่อเขียนรหัสเช่น:

Integer a = 1;
Integer b = 1;

Java เป็นฉลาดพอที่จะนำมาใช้ไม่เปลี่ยนรูปเดียวกันaและดังนั้นนี้เป็นจริง:b a == bอยากรู้อยากเห็นฉันเขียนตัวอย่างเล็ก ๆ เพื่อแสดงว่า java หยุดเพิ่มประสิทธิภาพด้วยวิธีนี้:

public class BoxingLol {
    public static void main(String[] args) {
        for (int i = 0; i < Integer.MAX_VALUE; i++) {
            Integer a = i;
            Integer b = i;
            if (a != b) {
                System.out.println("Done: " + i);
                System.exit(0);
            }
        }
        System.out.println("Done, all values equal");
    }
}

เมื่อฉันรวบรวมและเรียกใช้ (บนเครื่องของฉัน) ฉันจะได้รับ:

Done: 128

1
tl; dr -1 สำหรับการล้างมือ stackoverflow.com/questions/15052216/... stackoverflow.com/questions/20897020/... stackoverflow.com/questions/3131136/integers-caching-in-javaฯลฯ อธิบายในรายละเอียดเรื่องที่คุณกล่าวถึง; จะดีกว่าที่จะอ่านเอกสาร (หรือแหล่งที่มา lib) กว่าที่จะสร้างการทดสอบหลอกที่มีความเสี่ยงของท้องถิ่นสูงของผลลัพธ์ - ไม่เพียง แต่คุณลืมอย่างสมบูรณ์เกี่ยวกับขอบเขตล่างของแคช (เช่น -128 โดยค่าเริ่มต้น) ไม่เพียง คุณมีออฟ

แต่คุณไม่รับประกันว่าจะได้รับผลลัพธ์เดียวกันในเครื่องใด ๆ อย่างสมบูรณ์ - เนื่องจากคุณสามารถเพิ่มขนาดแคชได้ด้วยตัวเอง YMMV นอกจากนี้คำถามของ OP คือการเปรียบเทียบจำนวนเต็มสองตัวอย่างถูกต้องคุณยังไม่ได้ตอบเลย

ฉันเคารพความคิดเห็นและการรับรู้ของคุณที่นี่ ฉันคิดว่าเรามีวิธีการที่แตกต่างกันใน CS
Cory Kendall

1
มันไม่เกี่ยวกับความเห็นหรือการรับรู้ - มันเกี่ยวกับข้อเท็จจริงที่คุณพลาดไม่ได้ การทำแบบทดสอบหลอกพิสูจน์ว่าไม่มีสิ่งใดโดยไม่มีข้อมูลสำรองที่ยาก (เอกสารแหล่งที่มา ฯลฯ ) และหากไม่มีการตอบคำถามของ OP ไม่สมควรที่จะถูกเรียกว่าไม่ใช่คำตอบที่ดีและ CS ในฐานะที่เป็น "วิธีการที่แตกต่าง" - CS คือตามคำนิยามวิทยาศาสตร์ ; สิ่งที่คุณทำวิทยาศาสตร์ไม่ได้เป็น ; มันเป็นเรื่องไม่สำคัญที่ทำให้เข้าใจผิด (หรือมันจะเป็นความคิดเห็นที่น่าสนใจหากระบุไว้อย่างถูกต้อง) - หากคุณต้องการให้เป็นวิทยาศาสตร์ให้แก้ไขข้อบกพร่องพื้นฐานในคำตอบของคุณหรือ debunk พวกเขาอย่างสมเหตุสมผลว่า 'โรงงาน

แน่นอนฉันจะพยายามจัดการกับข้อบกพร่อง ฉันไม่ลืมเกี่ยวกับขอบเขตล่างฉันไม่รู้สึกว่ามันน่าสนใจและเลือกที่จะไม่รวมไว้ ฉันไม่เชื่อว่าฉันมีข้อผิดพลาดออกไปฉันระบุวิธีที่ java (ซึ่งฉันชี้แจงในเครื่องของฉันในสถานการณ์ของฉัน) หยุดการปรับให้เหมาะสมสิ่งนี้คือที่ 128 ซึ่งถ้าฉันได้ระบุค่าสูงสุดที่มันทำ สำหรับคำตอบของคุณถูกต้องกว่า 127
Cory Kendall

8

tl; drความคิดเห็นของฉันคือการใช้เอกภาพ+เพื่อเรียกใช้ unbox ในหนึ่งในตัวถูกดำเนินการเมื่อตรวจสอบความเท่าเทียมกันของค่าและเพียงใช้ตัวดำเนินการทางคณิตศาสตร์เป็นอย่างอื่น เหตุผลดังนี้

มันได้รับการกล่าวมาแล้วว่า==การเปรียบเทียบIntegerคือการเปรียบเทียบตัวตนซึ่งมักจะไม่ใช่สิ่งที่โปรแกรมเมอร์ต้องการและจุดมุ่งหมายคือการเปรียบเทียบมูลค่า ยังฉันได้ทำวิทยาศาสตร์เล็กน้อยเกี่ยวกับวิธีการเปรียบเทียบที่มีประสิทธิภาพมากที่สุดทั้งในแง่ของความกะทัดรัดโค้ดถูกต้องและความเร็ว

ฉันใช้วิธีการปกติ:

public boolean method1() {
    Integer i1 = 7, i2 = 5;
    return i1.equals( i2 );
}

public boolean method2() {
    Integer i1 = 7, i2 = 5;
    return i1.intValue() == i2.intValue();
}

public boolean method3() {
    Integer i1 = 7, i2 = 5;
    return i1.intValue() == i2;
}

public boolean method4() {
    Integer i1 = 7, i2 = 5;
    return i1 == +i2;
}

public boolean method5() { // obviously not what we want..
    Integer i1 = 7, i2 = 5;
    return i1 == i2;
}

และได้รับรหัสนี้หลังจากรวบรวมและ decompilation:

public boolean method1() {
    Integer var1 = Integer.valueOf( 7 );
    Integer var2 = Integer.valueOf( 5 );

    return var1.equals( var2 );
}

public boolean method2() {
    Integer var1 = Integer.valueOf( 7 );
    Integer var2 = Integer.valueOf( 5 );

    if ( var2.intValue() == var1.intValue() ) {
        return true;
    } else {
        return false;
    }
}

public boolean method3() {
    Integer var1 = Integer.valueOf( 7 );
    Integer var2 = Integer.valueOf( 5 );

    if ( var2.intValue() == var1.intValue() ) {
        return true;
    } else {
        return false;
    }
}

public boolean method4() {
    Integer var1 = Integer.valueOf( 7 );
    Integer var2 = Integer.valueOf( 5 );

    if ( var2.intValue() == var1.intValue() ) {
        return true;
    } else {
        return false;
    }
}

public boolean method5() {
    Integer var1 = Integer.valueOf( 7 );
    Integer var2 = Integer.valueOf( 5 );

    if ( var2 == var1 ) {
        return true;
    } else {
        return false;
    }
}

อย่างที่คุณเห็นได้อย่างชัดเจนวิธีที่ 1 โทรInteger.equals()(ชัด) วิธีที่ 2-4 ส่งผลให้เกิดรหัสเดียวกันโดยแกะค่าออก.intValue()มาแล้วเปรียบเทียบกับพวกเขาโดยตรงและวิธีที่ 5 เป็นการกระตุ้นการเปรียบเทียบตัวตนซึ่งเป็นวิธีที่ไม่ถูกต้อง เปรียบเทียบค่า

ตั้งแต่ (ดังที่ได้กล่าวไปแล้วโดยเช่น JS) equals()เกิดค่าใช้จ่าย (มันต้องทำinstanceofและไม่เลือกนักแสดง) วิธี 2-4 จะทำงานด้วยความเร็วเท่ากันอย่างเห็นได้ชัดดีกว่าวิธีที่ 1 เมื่อใช้ในลูปแน่นเนื่องจาก HotSpot ไม่ instanceofมีแนวโน้มที่จะเพิ่มประสิทธิภาพการปลดเปลื้องและ

มันค่อนข้างคล้ายกับตัวดำเนินการเปรียบเทียบอื่น ๆ (เช่น</ >) - พวกเขาจะทริกเกอร์ unboxing ในขณะที่ใช้compareTo()จะไม่ - แต่เวลานี้การดำเนินการจะปรับให้เหมาะสมโดย HS เนื่องจากintValue()เป็นเพียงวิธีการทะเยอทะยาน

ในความคิดของฉันไม่ค่อยใช้รุ่น 4 เป็นวิธีที่รัดกุมที่สุด - นักพัฒนา C / Java ทุกคนรู้ว่า unary plus เป็นกรณีส่วนใหญ่เท่ากับint/ ถึง.intValue()- ในขณะที่มันอาจเป็นช่วงเวลาWTFเล็กน้อยสำหรับบางคน ไม่ใช้ unary plus ในช่วงชีวิตของพวกเขา) มันแสดงให้เห็นถึงเจตนาที่ชัดเจนและชัดเจนที่สุด - มันแสดงให้เห็นว่าเราต้องการintคุณค่าของตัวถูกดำเนินการตัวหนึ่งบังคับให้ค่าอื่น ๆ ไปยัง unbox เช่นกัน นอกจากนี้ยังคล้ายกันมากที่สุดกับการi1 == i2เปรียบเทียบปกติที่ใช้สำหรับintค่าดั้งเดิม

คะแนนของฉันเป็นของi1 == +i2& i1 > i2สไตล์สำหรับIntegerวัตถุทั้งเหตุผลด้านประสิทธิภาพและความสอดคล้อง นอกจากนี้ยังทำให้โค้ดพกพาเป็นแบบดั้งเดิมโดยไม่ต้องเปลี่ยนแปลงสิ่งอื่นนอกจากการประกาศประเภท การใช้วิธีการที่ตั้งชื่อดูเหมือนว่าจะแนะนำเสียงความหมายให้ฉันคล้ายกับbigInt.add(10).multiply(-3)สไตล์ที่ถูกวิพากษ์วิจารณ์มาก


คุณสามารถอธิบายความหมายของ + ในวิธีที่ 4 ได้อย่างไร ฉันพยายาม google มัน แต่ฉันได้รับการใช้งานตามปกติของสัญลักษณ์นั้นเท่านั้น (นอกจากนี้การต่อข้อมูล)
Alex Li

1
@AlexLi มันหมายถึงสิ่งที่ฉันเขียน - unary +(unary plus) ดูเช่นstackoverflow.com/questions/2624410/…

8

การเรียกร้อง

if (a == b)

จะทำงานได้เกือบตลอดเวลา แต่ไม่รับประกันว่าจะใช้งานได้เสมอดังนั้นอย่าใช้งาน

วิธีที่เหมาะสมที่สุดในการเปรียบเทียบคลาสของ Integer สองคลาสเพื่อความเท่าเทียมกันโดยสมมติว่าชื่อ 'a' และ 'b' คือการเรียก:

if(a != null && a.equals(b)) {
  System.out.println("They are equal");
}

คุณสามารถใช้วิธีนี้ซึ่งเร็วกว่าเล็กน้อย

   if(a != null && b != null && (a.intValue() == b.intValue())) {
      System.out.println("They are equal");
    } 

ในเครื่องของฉันใช้งาน 99 พันล้านครั้งใช้เวลา 47 วินาทีโดยใช้วิธีแรกและ 46 วินาทีโดยใช้วิธีที่สอง คุณจะต้องทำการเปรียบเทียบค่าหลายพันล้านเพื่อดูความแตกต่าง

โปรดทราบว่า 'a' อาจเป็นโมฆะเนื่องจากเป็นวัตถุ การเปรียบเทียบด้วยวิธีนี้จะไม่ทำให้เกิดข้อยกเว้นตัวชี้ null

สำหรับการเปรียบเทียบมากขึ้นและน้อยกว่าให้ใช้

if (a != null && b!=null) {
    int compareValue = a.compareTo(b);
    if (compareValue > 0) {
        System.out.println("a is greater than b");
    } else if (compareValue < 0) {
        System.out.println("b is greater than a");
    } else {
            System.out.println("a and b are equal");
    }
} else {
    System.out.println("a or b is null, cannot compare");
}

1
if (a==b)ใช้งานได้กับค่าขนาดเล็กเท่านั้นและจะไม่ทำงานส่วนใหญ่
โทนี่

มันทำงานได้มากถึง 127 เนื่องจากเป็นแคชจำนวนเต็มเริ่มต้นของ Java ซึ่งทำให้แน่ใจว่าตัวเลขทั้งหมดถึง 127 มีค่าอ้างอิงเดียวกัน คุณสามารถตั้งค่าแคชให้สูงกว่า 127 หากคุณต้องการ แต่อย่าใช้ == เพื่อความปลอดภัย
otterslide

3

เราควรจะไปสำหรับวิธีเท่ากับ () สำหรับการเปรียบเทียบสำหรับสองจำนวนเต็มมันเป็นแนวทางปฏิบัติที่แนะนำ

ถ้าเราเปรียบเทียบจำนวนเต็มสองตัวโดยใช้ == ที่จะใช้ได้กับค่าจำนวนเต็มบางช่วง (จำนวนเต็มจาก -128 ถึง 127) เนื่องจากการปรับให้เหมาะสมภายในของ JVM

โปรดดูตัวอย่าง:

กรณีที่ 1:

จำนวนเต็ม a = 100 จำนวนเต็ม b = 100;

if (a == b) {
    System.out.println("a and b are equal");
} else {
   System.out.println("a and b are not equal");
}

ในกรณีข้างต้น JVM ใช้ค่าของ a และ b จากแคชพูลและส่งคืนอินสแตนซ์อ็อบเจ็กต์เดียวกัน (ดังนั้นที่อยู่หน่วยความจำ) ของวัตถุจำนวนเต็มและเราได้รับทั้งสองเท่ากันมันเพิ่มประสิทธิภาพ JVMสำหรับค่าบางช่วง

กรณีที่ 2:ในกรณีนี้ a และ b ไม่เท่ากันเนื่องจากไม่ได้มีช่วงตั้งแต่ -128 ถึง 127

จำนวนเต็ม a = 220; จำนวนเต็ม b = 220;

if (a == b) {
    System.out.println("a and b are equal");
} else {
   System.out.println("a and b are not equal");
}

วิธีการที่เหมาะสม:

Integer a = 200;             
Integer b = 200;  
System.out.println("a == b? " + a.equals(b)); // true

ฉันหวังว่านี่จะช่วยได้.


1

ในกรณีของฉันฉันมีการเปรียบเทียบสองIntegers nullเพื่อความเท่าเทียมกันที่ทั้งสองของพวกเขาอาจจะ ค้นหาหัวข้อที่คล้ายกันไม่พบสิ่งใดที่สวยงามสำหรับเรื่องนี้ มาด้วยฟังก์ชั่นยูทิลิตี้ที่เรียบง่าย

public static boolean integersEqual(Integer i1, Integer i2) {
    if (i1 == null && i2 == null) {
        return true;
    }
    if (i1 == null && i2 != null) {
        return false;
    }
    if (i1 != null && i2 == null) {
        return false;
    }
    return i1.intValue() == i2.intValue();
}

//considering null is less than not-null
public static int integersCompare(Integer i1, Integer i2) {
    if (i1 == null && i2 == null) {
        return 0;
    }
    if (i1 == null && i2 != null) {
        return -1;
    }
    return i1.compareTo(i2);
}

-1

เพราะวิธีการ comparaison จะต้องทำตาม type int (x == y) หรือ Class Integer (x.equals (y)) ที่มีตัวดำเนินการทางขวา

public class Example {

    public static void main(String[] args) {
     int[] arr = {-32735, -32735, -32700, -32645, -32645, -32560, -32560};

        for(int j=1; j<arr.length-1; j++)
            if((arr[j-1]!=arr[j]) && (arr[j]!=arr[j+1])) 
                System.out.println("int>"+arr[j]);


    Integer[] I_arr = {-32735, -32735, -32700, -32645, -32645, -32560, -32560};

        for(int j=1; j<I_arr.length-1; j++)
            if((!I_arr[j-1].equals(I_arr[j])) && (!I_arr[j].equals(I_arr[j+1]))) 
                System.out.println("Interger>"+I_arr[j]);
    }
}

-2

วิธีนี้เปรียบเทียบจำนวนเต็มสองตัวกับการตรวจสอบค่า null ดูการทดสอบ

public static boolean compare(Integer int1, Integer int2) {
    if(int1!=null) {
        return int1.equals(int2);
    } else {
        return int2==null;
    }
    //inline version:
    //return (int1!=null) ? int1.equals(int2) : int2==null;
}

//results:
System.out.println(compare(1,1));           //true
System.out.println(compare(0,1));           //false
System.out.println(compare(1,0));           //false
System.out.println(compare(null,0));        //false
System.out.println(compare(0,null));        //false
System.out.println(compare(null,null));     //true

4
สำหรับเรื่องนี้ฉันคิดว่ามันจะดีกว่าที่จะใช้Objects.equals(x,y)วิธีการแทนการกลิ้งของคุณเอง
ryvantage
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.