Variables


You declare variables in C# using the following syntax:

datatype identifier; 

For example:

 int i; 

This statement declares an int named i. The compiler won't actually let you use this variable until you have initialized it with a value, but the declaration allocates four bytes on the stack to hold the value.

Once it has been declared, you can assign a value to the variable using the assignment operator, =:

 i = 10; 

You can also declare the variable and initialize its value at the same time:

 int i = 10; 

This syntax is identical to C++ and Java syntax but very different from Visual Basic syntax for declaring variables. If you are coming from Visual Basic 6, you should also be aware that C# doesn't distinguish between objects and simple types, so there is no need for anything like the Set keyword, even if you want your variable to refer to an object. The C# syntax for declaring variables is the same no matter what the data type of the variable.

If you declare and initialize more than one variable in a single statement, all of the variables will be of the same data type:

 int x = 10, y =20; // x and y are both ints 

To declare variables of different types, you need to use separate statements. Don't assign different data types within a multiple variable declaration:

 int x = 10; bool y = true;               // Creates a variable that stores true or false int x = 10, bool y = true;   // This won't  

Notice the // and the text after in the preceding examples. These are comments. The // character sequence tells the compiler to ignore the text that follows. Comments in code are further explained later in this chapter.

Initialization of Variables

Variable initialization demonstrates another example of C#'s emphasis on safety. Briefly, the C# compiler requires that any variable be initialized with some starting value before you refer to that variable in an operation. Most modern compilers will flag violations of this as a warning, but the ever-vigilant C# compiler treats such violations as errors. This prevents you from unintentionally retrieving junk values from memory that is left over from other programs.

C# has two methods for ensuring that variables are initialized before use:

  • Variables that are fields in a class or struct, if not initialized explicitly, are by default zeroed out when they are created.

  • Variables that are local to a method must be explicitly initialized in your code prior to any statements in which their values are used. In this case, the initialization doesn't have to happen when the variable is declared, but the compiler will check all possible paths through the method and will flag an error if it detects any possibility of the value of a local variable being used before it is initialized.

C#'s approach contrasts with that of C++, in which the compiler leaves it up to the programmer to make sure that variables are initialized before use, and that of Visual Basic, in which all variables are zeroed out automatically.

For example, you can't do the following in C#:

 public static int Main() { int d; Console.WriteLine(d);   // Can't do this! Need return 0; } 

Notice that this code snippet demonstrates defining Main() so it returns an int instead of void.

When you attempt to compile these lines, you will receive this kind of error message:

Use of unassigned local variable 'd'

The same rules apply to reference types as well. Consider the following statement:

 Something objSomething; 

In C++, this line would create an instance of the Something class on the stack. In C#, this same line of code would only create a reference for a Something object, but this reference does not yet actually refer to any object. Any attempt to call a method or property against this variable would result in an error.

Instantiating a reference object in C# requires use of the new keyword. You create a reference as shown in the previous example and then point the reference at an object allocated on the heap using the new keyword:

 objSomething = new Something(); // This creates a Something on the heap 

Variable Scope

The scope of a variable is the region of code from which the variable can be accessed. In general, the scope is determined by the following rules:

  • A field (also known as a member variable) of a class is in scope for as long as its containing class is in scope (this is the same as for C++, Java, and VB).

  • A local variable is in scope until a closing brace indicates the end of the block statement or method in which it was declared.

  • A local variable that is declared in a for, while, or similar statement is in scope in the body of that loop. (C++ developers will note that this is the same behavior as the ANSI standard for C++. Early versions of the Microsoft C++ compiler did not comply with this standard, but scoped such variables to remain in scope after the loop terminated.)

Scope clashes for local variables

It's common in a large program to use the same variable name for different variables in different parts of the program. This is fine as long as the variables are scoped to completely different parts of the program so there is no possibility for ambiguity. However, bear in mind that local variables with the same name can't be declared twice in the same scope, so you can't do this:

 int x = 20; // some more code int x = 30; 

Consider the following code sample:

 using System; namespace Wrox.ProCSharp.Basics { public class ScopeTest { public static int Main() { for (int i = 0; i < 10; i++) { Console.WriteLine(i); // i goes out of scope here // We can declare a variable named i again, because // there's no other variable for (int i = 9; i >= 0; i--) { Console.WriteLine(i); }   // i goes out of scope here return 0; } } } 

This code simply prints out the numbers from 0 to 9, and then back again from 9 to 0, using a for loop. The important thing to note is that you declare the variable i twice in this code, within the same method. You can do this because i is declared in two separate loops, so each i variable is local to its own loop.

Here's another example:

 public static int Main() { int j = 20; for (int i = 0; i < 10; i++) { int j = 30;   // Can't Console.WriteLine(j + i); } return 0; } 

If you try to compile this, you'll get an error:

ScopeTest.cs(12,14): error CS0136: A local variable named 'j' this scope because it would give a different meaning to 'j', in a 'parent or current' scope to denote something 

This is because the variable j, which is defined before the start of the for loop, is still in scope within the for loop, and won't go out of scope until the Main() method has finished executing. Although the second j (the illegal one) is in the loop's scope, that scope is nested within the Main() method's scope. The compiler has no way to distinguish between these two variables, so it won't allow the second one to be declared. This is again different from C++ where variable hiding is permitted.

Scope clashes for fields and local variables

In certain circumstances, however, you can distinguish between two identifiers with the same name (although not the same fully qualified name) and the same scope, and in this case the compiler will allow you to declare the second variable. The reason is that C# makes a fundamental distinction between variables that are declared at the type level (fields) and variables declared within methods (local variables).

Consider the following code snippet:

using System; namespace Wrox.ProCSharp.Basics {    class ScopeTest2    { static int j = 20; public static void Main() { int j = 30; Console.WriteLine(j); return; }    } }

This code will compile, even though you have two variables named j in scope within the Main() method: the j that was defined at the class level, and doesn't go out of scope until the class is destroyed (when the Main() method terminates, and the program ends); and the j defined in Main(). In this case, the new variable named j that you declare in the Main() method hides the class-level variable with the same name, so when you run this code, the number 30 will be displayed.

However, what if you want to refer to the class-level variable? You can actually refer to fields of a class or struct from outside the object, using the syntax object.fieldname. In the previous example, you are accessing a static field (we look at what this means in the next section) from a static method, so you can't use an instance of the class; you just use the name of the class itself:

... public static void Main() {    int j = 30; Console.WriteLine(ScopeTest2.j); } ...

If you were accessing an instance field (a field that belongs to a specific instance of the class), you would need to use the this keyword instead. This keyword performs the same role as this in C++ and Java, and Me in Visual Basic.

Constants

Prefixing a variable with the const keyword when it is declared and initialized designates that variable as a constant. As the name implies, a constant is a variable whose value cannot be changed throughout its lifetime:

 const int a = 100; // This value cannot be changed 

Constants will be familiar to Visual Basic and C++ developers. C++ developers should, however, note that C# does not permit all the subtleties of C++ constants. In C++, not only could variables be declared as constant, but depending on the declaration, you could have constant pointers, variable pointers to constants, constant methods (that don't change the contents of the containing object), constant parameters to methods, and so on. These subtleties have been discarded in C#, and all you can do is declare local variables and fields to be constant.

Constants have the following characteristics:

  • They must be initialized when they are declared, and once a value has been assigned, it can never be overwritten.

  • The value of a constant must be computable at compile time. Therefore, you can't initialize a constant with a value taken from a variable. If you need to do this, you will need to use a read- only field (this is explained in Chapter 3, "Objects and Types").

  • Constants are always implicitly static. However, notice that you don't have to (and, in fact, are not permitted to) include the static modifier in the constant declaration.

At least three advantages exist to using constants in your programs:

  • Constants make your programs easier to read by replacing magic numbers and strings with readable names whose values are easy to understand.

  • Constants make your programs easier to modify. For example, assume that you have a SalesTax constant in one of your C# programs, and that constant is assigned a value of 6 percent. If the sales tax rate changes at a later point in time, you can modify the behavior of all tax calculations simply by assigning a new value to the constant; you don't have to hunt throughout your code for the value .06 and change each one, hoping that you've found all of them.

  • Constants make it easier to avoid mistakes in your programs. If you attempt to assign another value to a constant somewhere in your program other than at the point where the constant is declared, the compiler will flag the error.




Professional C# 2005
Pro Visual C++ 2005 for C# Developers
ISBN: 1590596080
EAN: 2147483647
Year: 2005
Pages: 351
Authors: Dean C. Wills

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net