Variable declarations following if statements
The C# language specification distinguishes between three types of statements (see chapter 8 for more details). In general you can have these statements:
- labeled-statement - my guess that this is for the old-fashioned
goto
statement - declaration-statement - which would be a variable declaration
- embedded-statement - which includes pretty much all the remaining statements
In the if
statement the body has to be embedded-statement, which explains why the first version of the code doesn't work. Here is the syntax of if
from the specification (section 8.7.1):
if ( boolean-expression ) embedded-statement
if ( boolean-expression ) embedded-statement else embedded-statement
A variable declaration is declaration-statement, so it cannot appear in the body. If you enclose the declaration in brackets, you'll get a statement block, which is an embedded-statement (and so it can appear in that position).
C - Variable Declaration in If Condition Available in Else?
You can't declare a variable like this
if((int a = 0))
The compiler does not allow the code to run and you get an error
and if you try this
if(something_that_is_false){
int a = 12;
}
else{
do_something;
}
again error because they are on the same level and they do not have access to their local variables.
Warning: you can use this code and runs without error
int a;
if(a=0){
printf("True");
}
else{
printf("False");
}
and you will see 'False' in screen because It's like writing
if(0) // and its false!
and for the last
int a;
if(a=0){
printf("True");
}
else{
printf("False");
}
you will see 'True' in screen because It's like writing
if(5) // any number other than zero is true!
Why can't variables be declared in an if statement?
Why? There can be no code path leading to the program assigning 1 to b without declaring it first.
You are right, but the compiler doesn't know that. The compiler does not execute the code. The compiler only translates to bytecode without evaluating expressions.
javascript variable declaration in the if/else loop
You can just declare let hello=''
at the beginning of the code:
As let
variable have the scope inside the brackets of them { }
...
The let statement declares a block-scoped local variable, optionally
initializing it to a value.
Read More:
What's the difference between using "let" and "var"?
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/let
var test = 4;
let hello = "";
if (test > 3) {
hello = "hello world";
} else {
hello = "hello gold";
}
console.log(hello);
Why is variable declared in an if-statement still in scope in else block?
Why is variable declared in an if-statement still in scope in else block?
Because the standard says that it is. It was designed so presumably because it is useful.
- How is this possible?
It's unclear why it wouldn't be possible.
I always thought that scope of such variables ends with the if-block.
You assumed wrongly.
I'd be thankful for quotation from the standard if possible. [language-lawyer]
Latest draft says:
[stmt.select.general]
Selection statements choose one of several flows of control.
selection-statement:
- ...
- if constexpropt ( init-statementopt condition ) statement else statement
- ...
Note that the entire if (condition) statement else statement
is a selection-statement.
[basic.scope.block]
Each
- selection or iteration statement ([stmt.select], [stmt.iter]),
- ...
introduces a block scope that includes that statement or handler.
Note that the condition is directly within the if-statement and not inside a sub-statement, and thus a declaration within it extends until the end of the entire block scope, which contains both the if-sub-statement, and the else-sub-statement (not standard names for those sub-statements).
There is also a pretty clear example that demonstrates ill-formed re-declarations, and incidentally shows the scope of such declaration:
if (int x = f()) {
int x; // error: redeclaration of x
}
else {
int x; // error: redeclaration of x
}
- If it's legal though, shouldn't it at least generate a warning?
Yeah, it would be nice if compilers were able to detect all provable null pointer indirections at compile time. It may be worth submitting a feature request regarding this corner case.
Are there any reasonable applications of such feature?
Sure. Following fabricated example seems reasonable to me:
if (Response r = do_request()) {
log << "great success. content: " << r.content;
} else {
log << "someone broke it :( error: " << r.error_code;
}
Or if you dislike implicit conversions:
if (Response r = do_request(); r.is_success()) {
Java Declaring a variable in an if-statement
When you scope a variable, it will only be available in that scope.
if (stuff) {
int i;
// i available here
}
// i not available here
The first type, the compiler doesn't know if you will use the variable later. it doesn't think there's anything wrong with creating a variable in that block.
In the second type, the compiler knows there is only one statement, because you didn't create a {}
block. The variable that you created will definitely not be used, so the compiler is alerting you that you will never be able to use the variable that you defined there.
Why a short variable declaration in an else if statement doesn't fail to compile even though no new variable is being defined on the left side?
From the Go specs, here is how an if
statement is defined:
IfStmt = "if" [ SimpleStmt ";" ] Expression Block [ "else" ( IfStmt | Block ) ] .
Later on, in the Declarations and Scope sections it is said:
An identifier declared in a block may be redeclared in an inner block. While the identifier of the inner declaration is in scope, it denotes the entity declared by the inner declaration.
Now, the if
statement is an implicit block:
Each "if", "for", and "switch" statement is considered to be in its own implicit block.
Then as you can see from the IfStmt
definition, after the keyword else
may come:
- a
Block
, i.e.else { /* code */ }
- an
IfStmt
again, as in your case, i.e.else if /* statement */ { /* code */ }
. This means theIfStmt
is recursive, and it is an implicit block within anotherIfStmt
(still an implicit block). Therefore it meets the condition for redeclaring the identifier.
Compare also with explicit blocks:
func foo() {
x := 10
{
x := 20
fmt.Println("Inner x:", x) // 20
}
fmt.Println("Outer x:", x) // 10
}
Declare variable in if statement (ANSI C)
No, you cannot do that.
What you can do is create a compound statement (anonymous or hanging block) just for the if
{
int variable;
variable = some_function();
if (variable) return 1;
}
/* variable is out of scope here */
Note that for this simple case you can call the function as the condition of the if
(no need for an extra variable)
if (some_function()) return 1;
C++, variable declaration in 'if' expression
As of C++17 what you were trying to do is finally possible:
if (int a = Func1(), b = Func2(); a && b)
{
// Do stuff with a and b.
}
Note the use of ;
of instead of ,
to separate the declaration and the actual condition.
Related Topics
How to Format Timespan in Xaml
Determine Number of Pages in a PDF File
Is This a Bad Practice to Catch a Non-Specific Exception Such as System.Exception? Why
How to Detect If MAChine Is Joined to Domain
How to Put Conditional Required Attribute into Class Property to Work with Web API
Impersonate User in Windows Service
Linq: Passing Lambda Expression as Parameter to Be Executed and Returned by Method
System.Io.File.Create Locking a File
Frombluetoothaddressasync Iasyncoperation Does Not Contain a Definition for 'Getawaiter' Error
Ssis Task for Inconsistent Column Count Import
Why Won't Anyone Accept Public Fields in C#
Formatting Datetime in ASP.NET Core 3.0 Using System.Text.JSON
Wpf Binding - Default Value for Empty String
How to Disable Cascade Delete for Link Tables in Ef Code-First
Where Are the Controllercontext and Viewengines Properties in MVC 6 Controller
Exceptions That Can't Be Caught by Try-Catch Block in Application Code
How to Check If Another Instance of the Application Is Running
With Rx, How to Ignore All-Except-The-Latest Value When My Subscribe Method Is Running