Functions comprise statements that execute sequentially in the
textual order in which they appear. A statement block
is a series of statements appearing between braces (the {}
tokens).
A declaration statement declares a new variable, optionally initializing the variable with an expression. A declaration statement ends in a semicolon. You may declare multiple variables of the same type in a comma-separated list. For example:
bool rich = true, famous = false;
A constant declaration is like a variable declaration, except that it cannot be changed after it has been declared, and the initialization must occur with the declaration (more on this in Constants):
const
double c = 2.99792458E08;
Expression statements are expressions that are also valid statements. In practice, this means expressions that “do” something; in other words, expressions that:
Assign or modify a variable
Instantiate an object
Call a method
Expressions that do none of these are not valid statements:
string s = "foo"; s.Length; // Illegal statement: does nothing!
When you call a constructor or a method that returns a value, you’re not obliged to use the result. However, unless the constructor or method changes state, the statement is useless:
new StringBuilder(); // Legal, but useless x.Equals (y); // Legal, but useless
Selection statements conditionally control the flow of program execution.
An if
statement
executes a statement if a bool
expression is true. For example:
if (5 < 2 * 3) Console.WriteLine ("true"); // true
The statement can be a code block:
if (5 < 2 * 3) { Console.WriteLine ("true"); // true Console.WriteLine ("...") }
An if
statement can
optionally feature an else
clause:
if (2 + 2 == 5) Console.WriteLine ("Does not compute"); else Console.WriteLine ("False"); // False
Within an else
clause, you
can nest another if
statement:
if (2 + 2 == 5) Console.WriteLine ("Does not compute"); elseif (2 + 2 == 4)
Console.WriteLine ("Computes"); // Computes
An else
clause always applies to the immediately preceding
if
statement in the statement
block. For example:
if (true) if (false) Console.WriteLine(); else Console.WriteLine ("executes");
This is semantically identical to:
if (true) { if (false) Console.WriteLine(); else Console.WriteLine ("executes"); }
We can change the execution flow by moving the braces:
if (true) { if (false) Console.WriteLine(); } else Console.WriteLine ("does not execute");
C# has no “elseif” keyword; however, the following pattern achieves the same result:
static void TellMeWhatICanDo (int age) { if (age >= 35) Console.WriteLine ("You can be president!");else if
(age >= 21) Console.WriteLine ("You can drink!");else if
(age >= 18) Console.WriteLine ("You can vote!"); else Console.WriteLine ("You can wait!"); }
switch
statements let you branch program execution based on a
selection of possible values that a variable may have. switch
statements may result in cleaner code
than multiple if
statements, since
switch
statements require an
expression to be evaluated only once. For instance:
static void ShowCard (int cardNumber) { switch (cardNumber) { case 13: Console.WriteLine ("King"); break; case 12: Console.WriteLine ("Queen"); break; case 11: Console.WriteLine ("Jack"); break; default: // Any other cardNumber Console.WriteLine (cardNumber); break; } }
You can only switch on an expression of a type that can be
statically evaluated, which restricts it to the string
type, the built-in integral types,
the enum
types, and nullable
versions of these (see Nullable Types).
At the end of each case
clause, you must say explicitly where execution is to go next, with
some kind of jump statement. Here are the options:
When more than one value should execute the same code, you can
list the common case
s
sequentially:
switch (cardNumber) {case 13:
case 12:
case 11:
Console.WriteLine ("Face card"); break; default: Console.WriteLine ("Plain card"); break; }
This feature of a switch
statement can be pivotal in terms of producing cleaner code than
multiple if
-else
statements.
C# enables a sequence of statements to execute repeatedly
with the while
, do
-while
,
for
, and foreach
statements.
while
loops repeatedly execute a body of code while a bool
expression is true. The expression is
tested before the body of the loop is executed.
For example, the following writes 012
:
int i = 0; while (i < 3) { // Braces here are optional Console.Write (i++); }
do
-while
loops differ in functionality from
while
loops only in that they test
the expression after the statement block has
executed (ensuring that the
block is always executed at least once). Here’s the preceding example
rewritten with a do
-while
loop:
int i = 0; do { Console.WriteLine (i++); } while (i < 3);
for
loops are like while
loops with special clauses for initialization and
iteration of a loop variable. A for
loop contains three clauses as
follows:
for (init-clause
;condition-clause
;iteration-clause
)statement-or-statement-block
The init-clause executes before the loop begins, and typically initializes one or more iteration variables.
The condition-clause is a bool
expression which is tested before each loop
iteration. The body executes while this condition is true.
The iteration-clause is executed after each iteration of the body. It’s typically used to update the iteration variable.
For example, the following prints the numbers 0 through 2:
for (int i = 0; i < 3; i++) Console.WriteLine (i);
The following prints the first 10 Fibonacci numbers (where each number is the sum of the previous two):
for (int i = 0, prevFib = 1, curFib = 1; i < 10; i++) { Console.WriteLine (prevFib); int newFib = prevFib + curFib; prevFib = curFib; curFib = newFib; }
Any of the three parts of the for
statement may be omitted. One can
implement an infinite loop such as the following (though while(true)
may be used instead):
for (;;) Console.WriteLine ("interrupt me");
The foreach
statement
iterates over each element in an enumerable object. Most of the types
in C# and the .NET Framework that represent a set or list of elements
are enumerable. For example, both an array and a string are
enumerable. Here is an example of enumerating over the characters in a
string, from the first character through to the last:
foreach (char c in "beer") Console.WriteLine (c + " "); // b e e r
We define enumerable objects in Enumeration and Iterators.
The C# jump statements are break
, continue
, goto
, return
, and throw
. We cover the throw
keyword in try Statements and Exceptions.
The break
statement ends
the execution of the body of an iteration or switch
statement:
int x = 0;
while (true)
{
if (x++ > 5) break
; // break from the loop
}
// execution continues here after break
...
The continue
statement
forgoes the remaining statements in the loop and makes an early start
on the next iteration. The following loop skips
even numbers:
for (int i = 0; i < 10; i++)
{
if ((i % 2) == 0) continue
;
Console.Write (i + " "); // 1 3 5 7 9
}
The goto
statement
transfers execution to a label (denoted with a colon suffix) within a
statement block. The following iterates the numbers 1 through 5,
mimicking a for
loop:
int i = 1;startLoop:
if (i <= 5) { Console.Write (i + " "); // 1 2 3 4 5 i++;goto startLoop;
}
The return
statement
exits the method and must return an expression of the method’s return
type if the method is nonvoid:
static decimal AsPercentage (decimal d) { decimal p = d * 100m; return p; // Return to calling method with value }
A return
statement can appear
anywhere in a method (except in a finally
block).