'if'문의 끝에 세미콜론
오늘 30 분 동안 버그를 검색 한 끝에 다음과 같이 코드 대신 if 문 뒤에 세미콜론을 넣을 수 있음을 발견했습니다.
if(a == b);
// Do stuff
이것은 기본적으로 a
동일 b
하든 그렇지 않든간에 일이 수행 될 것이라는 것을 의미하며, 그 if
진술에는 아무런 의미가 없습니다. Java에서 오류가 발생하지 않는 이유는 무엇입니까? 이것이 유용한 상황이 있습니까?
왜 발생합니까?
Java 언어 사양 은 다음과 같이 말합니다.
빈 진술
빈 문은 아무것도하지 않습니다.
EmptyStatement: ;
빈 명령문의 실행은 항상 정상적으로 완료됩니다.
본질적으로 a == b 인 경우 빈 문을 실행하려는 것을 의미합니다.
if(a == b);
무엇을해야합니까?
이 문제에 대한 두 가지 주요 솔루션이 있습니다.
코드 포맷터를 사용하고 내부 항목
if
을{
및으로 둘러싸면 빈 문 문제를 피할 수 있습니다}
. 이렇게하면 빈 문장이 훨씬 더 읽기 쉬워집니다.if(a == b){ ; }
다음과 같은 정적 코드 분석에 사용되는 도구를 확인할 수도 있습니다.
이러한 문제를 즉시 강조 할 수 있습니다.
두 솔루션을 결합하는 것이 좋습니다.
이것이 유용한 상황이 있습니까?
유능한? "코드를 더 깨끗하고, 더 명확하고, 더 빠르고, 더 쉽게 유지 관리 할 수있게 만듭니다"에서처럼? 전혀. 이것은 가난하고 혼란스러운 코드 일 가능성이 큽니다 .
그러나 반드시 양성일 필요는 없습니다 . 이러한 문은 부작용을 일으키는 메서드로 인해 작업을 수행하거나 상태를 변경할 수 있으며 선택적 으로 연산자 단락 으로 인해 해당 메서드를 평가할 수 있습니다.
if( a() && b() );
여기에서 a()
또는 b()
무언가를 할 수 있으며 true 인 b()
경우에만 실행됩니다 a()
.
이유에 관해서 는, while(reader.read());
잘못된 코드를 작성하는 개발자의 대안보다 정의되고 예상되는 동작 (예 : 같은 명령문 ) 에서 벗어나는 것이 더 나쁠 것이라 생각합니다 .
잘못된 코드를 작성하는 것은 항상 가능합니다. 그리고 다시 말하면, 이것은 거의 모든 경우에 나쁜 코드가 될 것입니다.
가능한 사용 사례 :
if (a==b);
else {
// Do something
}
좋지는 않지만 가능합니다.
그래도 Java 사양은 빈 if
.
Eclipse를 사용하는 경우 해당 명령문에 대해 경고하도록 만들 수 있습니다.
if
문 을 사용하는 if
경우 조건이 참이면 다음의 첫 번째 문 이 실행됩니다. if
(중괄호 포함) 뒤에 블록이 있으면 해당 전체 블록에 대해 계산됩니다. 블록이 없으면 하나의 명령문에 대해서만 계산됩니다. 단일 세미콜론은 빈 문입니다. 다음과 같이 예제에서 코드를 작성할 수도 있습니다.
if(a==b) {
;
}
표현과 문장을 구별하기 위해 통사적인 설탕이 더 많았던 시절의 오래된 남은 것입니다.
기본적으로 쉼표는 목록 항목 구분 기호로 사용되었으므로 세미콜론은 "문 목록"구분 기호로 사용되었습니다. 단점은 목록의 null 항목과 블록의 null 문을 처리하는 것입니다.
항목 목록에서 Java는 명시 적 키워드 null
를 사용하지만 "null 문"은 빈 줄일뿐입니다. 빈 줄의 존재를 허용하는 것은 C에서 물려받은 전통에서 이어집니다.
왜 그럴까요? 특히 if
명령문이 실행되고 있지 않다는 것을 알고있는 경우 : 일부 if 문에는 부작용이 있기 때문입니다.
int c;
if ((c = in.read()) != -1);
예, 최선의 예는 아니지만 기본적으로 스트림에서 바이트를 읽고 아무것도하지 않는다고 말합니다. 일부 코너 경우에 유용 할 수 있지만이 예제가 최선이 아니더라도 의도를 보여줍니다. 실수로 문장을 실행하지 않고 표현의 부작용을 느끼고 싶습니다.
유용 할 때가 생각 나지 않습니다. 다음과 같은 루프에 유용 할 수 있습니다.
while(do something);
또는
for(init; do something; something else);
IDE에서 코드 서식을 정기적으로 사용하면 이러한 종류의 버그가 분명해집니다. 일부 IDE에서는이를 가능한 버그로 강조하기도합니다.
인간에게는 유용한 목적이 없다는 데 동의합니다. 언어 정의를 단순화하기 때문에 거기에 있다고 생각합니다. if
예 를 들어 an 뒤에 오는 것은 e 뒤에 오는 것과 동일 하다는 것을 의미 while
합니다.
왜? 컴파일러 작성자에게 더 쉽기 때문입니다. 세미콜론을 확인하기 위해 특별한 경우를 만들 필요가 없으며 if(cond)
허용하는 추가 사용법이 있습니다.
if (cond && maybeFunc())
;// Code here I want to ignore
실제로 이것을 허용하는 것은 끔찍한 생각이지만. 이를 확인하기 위해 허용 한 다음 케이스를 추가하는 것이 더 쉽습니다.
Java는 명령문 블록이 허용되는 모든 위치에 빈 블록을 허용합니다. 나는 이것을 모든 블록에 대한 일반적인 규칙으로 만드는 것이 컴파일러를 단순화한다고 확신합니다.
나는 이것이 주로 발견하기 어려운 버그의 원인이라는 데 동의합니다. 저는 항상 블록 주위에 중괄호를 사용합니다. 문장이 하나 일 때에도 Java에서는 언제든지 중괄호로 블록을 만들 수 있으므로 중괄호를 사용하면이 운명에서 벗어날 수 없습니다. 예를 들어, 다음과 같은 것을 찾으려고 4 시간을 낭비한 적이 있습니다.
while (condition);
{
statement;
statement;
}
첫 번째 줄 끝에있는 세미콜론은 실수로 while 루프에 대한 문 블록을 비워 두었습니다. 구문이 유효하기 때문에 프로그램이 컴파일되고 정상적으로 실행되었습니다. 찾기 가 정말 어려웠습니다.
빈 블록을 가질 수 있다는 것이 매우 좋은 상황을 생각할 수 있습니다. 이것은 다음과 같습니다.
if (condition1) {
do_action_1();
}
else if (condition2) {
//nothing really to do in this case
}
else if (condition3) {
do_action2();
}
else {
do_action3();
}
위의 예에서 다양한 조건을 분리 할 수 있기를 원합니다. 이러한 조건이 겹칠 수 있으므로 항상 순서를 다시 정렬 할 수있는 것은 아닙니다. 조건 중 하나가 실제로 수행 할 필요가없는 경우 Java가 빈 블록을 가질 수 있도록 허용하는 것이 좋습니다. 그렇지 않으면 언어는 당신이 정말로 아무것도하고 싶지 않을 때 사용할 "noop"메소드의 어떤 형태를 필요로 할 것입니다.
개인적으로 명시적인 "noop"문을 선호하지만 Java가 정의 된 방식은 아닙니다.
유용성에 대한 FYI 및 그와 같은 진술이있는 경우 어떤 차이를 만들거나 만들 수 있는지
다음과 같은 코드를 고려하십시오.
int a = 10;
if ((a = 50) == 50);
System.out.println("Value of a = " + a);
분명히이 경우 if
문은 출력을 변경합니다. 따라서 이와 같은 진술은 차이를 만들 수 있습니다.
이것은 프로그램에 영향을 준다고 말하는 것이 유용하거나 더 나은 상황입니다.
if(a==b)
println("a equals b");
{}
실행할 줄이 하나뿐이면 IF 문을 사용할 수 있으므로 if(a==b);
같으면 실행하고 빈 문을 사용하여 ... 아무 일도하지 않고 정상적인 루프로 돌아갑니다. IF 블록의.
jls의 몇 가지 정의가이를 설명합니다 (14 장).
블록은 진술이다
여기 에 설명 된대로 a Block
는 a StatementWithoutTrailingSubstatement
이고, 차례로 a StatementNoShortIf
, 즉 a Statement
입니다. 따라서 이들 중 어느 것이 든 필요한 곳에 Block
.
if 절
이것도 for
및 while
루프 의 경우이지만-문을 사용할 if
것입니다. 이 규칙은 거의 동일합니다. 의 구문 설명은 여기if-statements
에서 찾을 수 있습니다 .
IfThenStatement:
if ( Expression ) Statement
IfThenElseStatement:
if ( Expression ) StatementNoShortIf else Statement
IfThenElseStatementNoShortIf:
if ( Expression ) StatementNoShortIf else StatementNoShortIf
여기에서 블록을 사용할 수 있습니다.
하지만 왜 작동합니까? ?
;
EmptyStatement
( 링크 ) 로 정의되며 StatementNoShortIf
. 그래서 코드의 조건부 조각처럼 if-statement
루프, 우리는 대체 할 수 Block
로모그래퍼 EmptyStatement
경우, StatementNoShortIf
또는하는 것은 Statement
필요합니다.
따라서 if(Expression)EmptyStatement
작동합니다.
왜 오류가 발생하지 않습니까?
Pretty simple: java gives an error if it finds invalid syntax. But if(Expression)EmptyStatement
is perfectly valid syntax. Instead javac
gives a warning if launched with the proper parameters. The full list of warnings that can be dis-/enabled lists the warning-name empty
for this purpose. So compilation with -Xlint:all
or -Xlint:empty
will generate a warning about this.
Your IDE should have an option to enable this kind of warning as well. For eclipse, see @nullptr's answer. In IntelliJ, you can press Ctrl + Shift + A
, enter empty body
into the search field and enable the warning (marked in the image)
What is this even used for?
To be honest, there's not much use in it from a minimalistic point of view. There's usually a way to get things done without a "do nothing" command. It's rather a question of personal preferences, whether you rather use
if( a() && b() );
or
if( a() ) b();
and same would apply to other cases, in which the EmptyStatement
is used. An important point to consider on this topic is readability of code. There are occasions, where code becomes more readable by using the no-op. On the other hand there are cases, where code becomes quite a lot harder to comprehend with using the EmptyStatement
- the above example would count to the later IMO.
Semicolon at the end of,
if(a==b); simply finish the statement in single line which means ignore the result of condition and continue the execution from the next line
This code is useful, on the other hand sometime introduce bug in program, for example,
case 1.
a = 5;
b = 3;
if(a == b);
prinf("a and b are equal");
case 2.
a = 5;
b = 5;
if(a == b);
prinf("a and b are equal");
would print the same output on the screen...
I can think of a scenario where an empty statement is required (not for if
condition but for while
loop).
When a program just want an explicit confirmation from the user to proceed. This may be required when the work after the user confirmation depends on some other things and user want to take control of when to proceed.
System.out.println("Enter Y to proceed. Waiting...");
System.out.println("");
while(!(new Scanner(System.in).next().equalsIgnoreCase("Y")));
System.out.println("Proceeding...");
// do the work here
look this:
int a,b,c = 0;
if(a == b){
c =1;
}
System.out.print(c);//1
so, you can write like this:
if (a == b)c=1;
but,if this code is this:
int a,b,c=0;
if (a != b){
}
if (a == b ){
c =1;
}
you can write like this:
if(a != b);
if(a == b )c=1;
so,you will know if(a != b);
do noting
The semi-colon in the if indicates the termination of the if condition as in java ;
is treated as the end of a statement, so the statement after if gets executed.
N by N 그리드의 doodads로 작업하고 랜덤 doodad의 특성을 위, 아래, 왼쪽 및 오른쪽의 특성과 비교하는 클래스에 대한 프로그래밍 과제를 작업하는 동안 중첩 된 문을 방지하기 위해 이것을 잘 사용하는 것을 발견했습니다. 잠재적 인 경계 예외. 내 목표는 코드를 최소화하고 if 문을 중첩하지 않는 것이 었습니다.
if (row == 0);
else (method (grid[row][col], grid[row-1][col]));
if (row == N-1);
else (method (grid[row][col], grid[row+1][col]));
if (col == 0);
else (method (grid[row][col], grid[row][col-1]));
if (col == N-1);<br>
else (method (grid[row][col], grid[row][col+1]));
method(Doodad a, Doodad b)
a와 b 사이에 어떤 작업이 있습니까 ?
또는 예외 처리를 사용하여이 구문을 피할 수 있지만 내 응용 프로그램에서 잘 작동하고 작동합니다.
참고 URL : https://stackoverflow.com/questions/14112515/semicolon-at-end-of-if-statement
'Program Tip' 카테고리의 다른 글
특정 문자가 문자열에 나타나는 횟수 (0) | 2020.11.16 |
---|---|
ExecutionPolicy 동작이 Visual Studio의 프로젝트마다 다른 이유는 무엇입니까? (0) | 2020.11.16 |
열거 형이 반복되지 않는 이유는 무엇입니까? (0) | 2020.11.16 |
C ++에서 typedef를 언제 사용해야합니까? (0) | 2020.11.16 |
ERRORLEVEL을 0으로 재설정하는 가장 쉬운 방법은 무엇입니까? (0) | 2020.11.16 |