Java 변수가 그 자체와 어떻게 다를 수 있습니까?
이 질문을 Java로 해결할 수 있는지 궁금합니다 (저는 언어를 처음 사용합니다). 다음은 코드입니다.
class Condition {
// you can change in the main
public static void main(String[] args) {
int x = 0;
if (x == x) {
System.out.println("Ok");
} else {
System.out.println("Not ok");
}
}
}
실습에서 다음과 같은 질문을 받았습니다. x == x
조건 자체를 수정하지 않고 첫 번째 사례를 건너 뛰려면 (즉, 조건을 false로 설정) 어떻게해야합니까?
한 가지 간단한 방법은 다음을 사용하는 것입니다 Float.NaN
.
float x = Float.NaN; // <--
if (x == x) {
System.out.println("Ok");
} else {
System.out.println("Not ok");
}
안좋아
으로도 똑같이 할 수 있습니다 Double.NaN
.
에서 JLS §15.21.1. 수치 평등 연산자 ==
및!=
:
부동 소수점 동등성 테스트는 IEEE 754 표준의 규칙에 따라 수행됩니다.
피연산자가 NaN이면의 결과
==
는false
이지만 결과는!=
입니다true
.실제로 테스트
x!=x
는true
의 값x
이 NaN 인 경우에만 수행됩니다 ....
int x = 0;
if (x == x) {
System.out.println("Not ok");
} else {
System.out.println("Ok");
}
에 의해 Java 언어 사양 NaN
과 동일하지 않습니다 NaN
.
따라서 다음과 같이 x
같게 된 모든 줄은 NaN
다음과 같이 발생합니다.
double x=Math.sqrt(-1);
Java 언어 사양에서 :
부동 소수점 연산자는 예외를 생성하지 않습니다 (§11). 오버플로하는 연산은 부호있는 무한대를 생성하고 언더 플로하는 연산은 비정규 화 된 값 또는 부호있는 0을 생성하며, 수학적으로 명확한 결과가없는 연산은 NaN을 생성합니다. NaN을 피연산자로 사용하는 모든 숫자 연산은 결과로 NaN을 생성합니다. 이미 설명했듯이 NaN은 순서가 지정되지 않았으므로 하나 또는 두 개의 NaN을 포함하는 숫자 비교 연산은 false를 반환합니다. 하고 NaN을 포함하는 모든! = 비교는 x가 NaN 일 때 x! = x를 포함하여 true를 반환합니다.
이것이 옵션인지 확실하지 않지만 변경 x
지역 변수에서 필드로 변경하면 다른 스레드가 if
문 에서 읽기 왼쪽과 오른쪽 사이에서 값을 변경할 수 있습니다 .
다음은 짧은 데모입니다.
class Test {
static int x = 0;
public static void main(String[] args) throws Exception {
Thread t = new Thread(new Change());
t.setDaemon(true);
t.start();
while (true) {
if (x == x) {
System.out.println("Ok");
} else {
System.out.println("Not ok");
break;
}
}
}
}
class Change implements Runnable {
public void run() {
while (true)
Test.x++;
}
}
산출:
⋮
Ok
Ok
Ok
Ok
Ok
Ok
Ok
Ok
Not ok
교체 된 줄을 읽을 수 있습니다.
double x = Double.NaN;
This would cause the gotcha to be printed.
JLS (Java Language Specification)는 다음과 같이 말합니다.
Floating-point operators produce no exceptions (§11). An operation that overflows produces a signed infinity, an operation that underflows produces a denormalized value or a signed zero, and an operation that has no mathematically definite result produces NaN. All numeric operations with NaN as an operand produce NaN as a result. As has already been described, NaN is unordered, so a numeric comparison operation involving one or two NaNs returns false and any != comparison involving NaN returns true, including x!=x when x is NaN.
I managed to get a Gotcha!
from this:
volatile Object a = new Object();
class Flipper implements Runnable {
Object b = new Object();
public void run() {
while (true) {
Object olda = a;
a = b;
a = olda;
}
}
}
public void test() {
new Thread(new Flipper()).start();
boolean gotcha = false;
while (!gotcha) {
// I've added everything above this - I would therefore say still legal.
if (a == a) {
System.out.println("Not yet...");
} else {
System.out.println("Gotcha!");
// Uncomment this line when testing or you'll never terminate.
//gotcha = true;
}
}
}
There are so many solutions:
class A extends PrintStream {
public A(PrintStream x) {super(x);}
public void println(String x) {super.println("Not ok");}
public static void main(String[] args) {
System.setOut(new A(System.out));
int x = 0;
if (x == x) {
System.out.println("Ok");
} else {
System.out.println("Not ok");
}
}
}
One easy solution is:
System.out.println("Gotcha!");if(false)
if( a == a ){
System.out.println("Not yet...");
} else {
System.out.println("Gotcha!");
}
But I don't know all the rules to this riddle...
:) I know that this is a cheat, but without knowing all rules, is this the easiest solution to the question :)
Create your own class System
in tha same package with Condition
.
In this case your System
class will hide java.lang.System
class
class Condition
{
static class System
{
static class out
{
static void println(String ignored)
{
java.lang.System.out.println("Not ok");
}
}
}
public static void main (String[] args) throws java.lang.Exception
{
int x = 0;
if (x == x)
{
System.out.println("Not ok");
}
else
{
System.out.println("Ok");
}
}
}
Using the same skip/change output approach from another answers:
class Condition {
public static void main(String[] args) {
try {
int x = 1 / 0;
if (x == x) {
System.out.println("Ok");
} else {
System.out.println("Not ok");
}
} catch (Exception e) {
System.out.println("Not ok");
}
}
}
참고URL : https://stackoverflow.com/questions/19416644/how-can-a-java-variable-be-different-from-itself
'program tip' 카테고리의 다른 글
NSAttributedString 추가 텍스트 정렬 (0) | 2020.08.08 |
---|---|
Android 대화 상자 : 제목 표시 줄 제거 (0) | 2020.08.08 |
내 프로젝트와 이러한 Javascript 프레임 워크에 대해 내가 잘못한 부분은 무엇입니까? (0) | 2020.08.08 |
'스텔스'웹 크롤러 감지 (0) | 2020.08.08 |
React Router v4-현재 경로를 얻는 방법? (0) | 2020.08.07 |