Java에서 두 정수를 올바르게 비교하려면 어떻게 해야 합니까?
상자 안의 원시 정수를 다음과 같은 상수와 비교하면 알 수 있습니다.
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)
?
아니요. 정수, 길이 등 사이의 ==는 기준 동일성을 확인합니다.
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);
is is is is is 。false
. " 자동 과 같은 결과를 할 수 "작은" 자동 상자 값을 삽입하면 다음과 같은 까다로운 결과를 초래할 수 있습니다.
Integer x = 10;
Integer y = 10;
System.out.println(x == y);
인쇄가 됩니다.true
(JLS 섹션 5.1.7).여전히 참고평등이 사용되고 있지만, 참고평등은 정말로 동등합니다.
박스화 되고 있는 값 p가 -128 ~127(이하 3.10.1), 부울 리터럴 true 또는 false(이하 3.10.3) 또는 "\u0000" ~ "\u007f" 사이의 문자 리터럴(이하 3.10.4)인 경우 a와 b는 p의 두 박스화 변환 결과입니다.a == b인 경우는 항상 있습니다.
개인적으로 사용하고 싶은 것:
if (x.intValue() == y.intValue())
또는
if (x.equals(y))
바와 래퍼는 (「 」의 「 」의 「 」의 「 」의 「 」의 「 」의 「 」의 「 」의 「 」의 「 」Integer
,Long
etc)및 유형예: etc)입니다.int
,long
etc) 래퍼 타입의 값을 언박스로 하고, 관련된 원시 값에 대해 시험을 적용한다.
이는 바이너리 수치 프로모션(JLS 섹션 5.6.2)의 일환으로 이루어집니다.각 오퍼레이터의 매뉴얼을 참조하여 적용 여부를 확인합니다.예를 들어, 의 문서로부터==
★★★★★★★★★★★★★★★★★」!=
(JLS 15.21.1):
등가 연산자의 피연산자가 양쪽 모두 수치형일 경우 또는 한쪽이 수치형일 경우(55.1.8), 다른 한쪽이 수치형으로 변환가능할 경우(55.6.2) 피연산자에 대해 이진수 수치 프로모션을 실시한다.
및을 and의 경우<
,<=
,>
★★★★★★★★★★★★★★★★★」>=
(JLS 15.20.1)
수치 비교 연산자의 각 피연산자 유형은 기본 수치 유형으로 변환할 수 있는 유형( be 5.1.8)이어야 합니다. 그렇지 않으면 컴파일 시 오류가 발생합니다.오퍼랜드(ands5.6.2)에 대해서 바이너리 수치 프로모션을 실시한다.오퍼랜드의 승격 유형이 int 또는 long일 경우 부호 있는 정수 비교가 실행됩니다.이 승격 유형이 float 또는 double일 경우 부동 소수점 비교가 실행됩니다.
어느 타입도 수치 타입이 아닌 상황에서는, 이 어느 것도 고려되지 않는 것에 주의해 주세요.
==
는 오브젝트 동일성을 테스트합니다.러나속속 쉽쉽쉽쉽쉽
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 모두).원시 상자 클래스는 불변하기 때문에 이것은 적절한 최적화입니다.
Java 1.7에서 Objects.equals를 사용할 수 있습니다.
java.util.Objects.equals(oneInteger, anotherInteger);
인수가 서로 같으면 true를 반환하고 그렇지 않으면 false를 반환합니다.따라서 양쪽 인수가 null이면 true가 반환되고 정확히1개의 인수가 null이면 false가 반환됩니다.그렇지 않으면 첫 번째 인수와 동등한 방법을 사용하여 동등성이 결정됩니다.
두 정수를 비교하려면 항상 equals() 메서드를 사용해야 합니다.추천하는 연습입니다.
==를 사용하여 두 정수를 비교하면 JVM의 내부 최적화로 인해 특정 정수 범위(-128 ~ 127)에 대해 작동합니다.
예를 참조해 주세요.
케이스 1:
Integer a = 100;
Integer 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의 범위가 아니기 때문에 동일하지 않습니다.
Integer a = 220;
Integer 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
내 의견은 단항식을 사용하는 것이다.+
값 동일성을 확인할 때 피연산자 중 하나에서 상자 해제를 트리거하고, 그렇지 않으면 단순히 산술 연산자를 사용합니다.을 사용하다
바와 같이==
에 대해서 설명하겠습니다.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;
}
컴파일과 디컴파일 후에 다음 코드를 얻었습니다.
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
그리고 체크되지 않은 캐스트)의 경우, HotSpot은 캐스트를 최적화하지 않을 가능성이 높기 때문에, 메서드 2-4는, 확실히 같은 속도로 동작합니다.타이트 루프에서 사용하는 경우는, 메서드 1보다 훨씬 낫습니다.instanceof
.
다른 비교 연산자와 매우 유사합니다(예:<
/>
) - 사용 중 언박싱을 트리거합니다.compareTo()
하지만 이번에는 HS에 의한 조작의 최적화가 매우 용이하기 때문입니다.intValue()
겟터 방식일 뿐입니다(최적화를 위한 주요 후보).
거의 사용하지 않는 버전4가 가장 간결한 방법이라고 생각합니다.노련한 C/Java 개발자는 Unary Plus가 대부분의 경우 캐스팅과 동등하다는 것을 알고 있습니다.int
/.intValue()
- 일부(대부분 평생 단항 플러스를 사용하지 않은 사람들)에게는 약간의 WTF 순간이 될 수 있지만, 그것은 거의 틀림없이 가장 명확하고 가장 간결하게 의도를 보여준다 - 그것은 우리가 원하는 것을 보여준다.int
피연산자 중 하나의 값, 다른 값도 강제로 언박스로 합니다.그것은 또한 논쟁의 여지없이 일반과 가장 유사하다.i1 == i2
원시적인 것에 사용되는 비교int
가치.
제 투표는i1 == +i2
&i1 > i2
을 위해 스타일링하다.Integer
오브젝트에는 퍼포먼스와 일관성이 있습니다.또, 타입 선언 이외의 변경은 일절 하지 않고, 코드를 프리미티브에 이식할 수 있도록 합니다.명명된 방법을 사용하는 것은 나에게 시멘틱 노이즈를 도입하는 것처럼 보인다, 많은 비난을 받는 것과 비슷하다.bigInt.add(10).multiply(-3)
스타일.
==
단, 다음과 같은 코드를 쓸 때는 참조가 동일한지 여부를 확인합니다.
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
부르기
if (a == b)
대부분의 경우 작동하지만 항상 작동한다고 보장되지는 않으므로 사용하지 마십시오.
이름이 '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");
}
제 기계에서는 첫 번째 방법으로는 990억 번의 조작이 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");
}
내 경우엔 두 가지를 비교해야 했다.Integer
둘 다 있을 수 있는 평등을 위해 snull
비슷한 주제를 찾아봤는데 우아한 게 없네요.간단한 유틸리티 기능이 떠올랐습니다.
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);
}
비교 방법은 올바른 연산자와의 유형 int(x==y) 또는 클래스 정수(x.tegrate(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]);
}
}
이 메서드는 두 Integer를 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
언급URL : https://stackoverflow.com/questions/1514910/how-can-i-properly-compare-two-integers-in-java
'programing' 카테고리의 다른 글
Vuex getter가 null을 반환함 (0) | 2022.08.12 |
---|---|
라이브러리가 -g로 컴파일되었는지 어떻게 알 수 있습니까? (0) | 2022.08.12 |
스프링 데이터 JPA - "유형에 대한 속성을 찾을 수 없습니다" 예외 (0) | 2022.08.12 |
Vuex 모듈은 다른 Vuex 모듈을 감시할 수 있습니까? (0) | 2022.08.12 |
vue SSR를 사용하여 루트 가드 내의 스토어에 어떻게 액세스합니까? (0) | 2022.08.12 |