Microsoft Visual C# 2005 Express Edition: Build a Program Now! (28 page)

Read Microsoft Visual C# 2005 Express Edition: Build a Program Now! Online

Authors: Patrice Pelland

Tags: #General, #Computers, #C♯ (Computer program language), #Programming Languages, #C#, #Microsoft .NET Framework, #Computer Books: Languages, #Computer Graphics, #Application software, #C# (Computer program language), #Programming, #Microsoft Visual C# .NET, #Microsoft Visual C♯ .NET, #Electronic books, #Game Programming & Design, #Computing: Professional & Programming, #C (Computer program language), #Computers - Languages, #Programming Languages - C#, #Programming & scripting languages: general

BOOK: Microsoft Visual C# 2005 Express Edition: Build a Program Now!
9.91Mb size Format: txt, pdf, ePub

keywords.

source code of the ReadFile method.

The ReadToEnd method reads the content of the opened file and puts it in a string variable. Press 5
Shift+F11
and then
F11
. A message box should display the string variable content. Click
OK
in the message box. You should now be back at the caller.

Step into the code until you get the string Helloworld in a message box. Pay attention to the order of 6 execution and look into the variables and into the content in each of the tab sections. 7 Step into the code again to get into the ManipulateStrings method.
Chapter 7: Fixing the Broken Blocks

119

C07622299.indd 119

C07622299.indd 119

10/24/05 7:13:57 PM

10/24/05 7:13:57 PM

The first instruction in the ManipulateStrings method is taking the string received in argument and converting it to an array of characters. The reason this is done is because strings are immutable in .NET, and therefore you have to work with them in read-only mode once they’re created. Methods modifying a string are actually returning a new string object that contains the modification applied to it.

M O R E I N F O

As you can see in the source code, one of the ManipulateStrings arguments,
myString, is passed with the ref keyword. When you have an argument that
is passed to a method by reference, the called method is receiving a refer-
ence to the same memory location used by the caller. Therefore, if the meth-
od is modifying the content of that argument, it is modifying the content at
this memory location and thus modifying the variable from the caller. In this
case, anything that is done to the myString argument will modify the value
of the variable in the calling code. The other argument is myPosition, and it
is passed by value. When you have an argument that is passed by value, the
method is receiving a copy of the variable from the calling code and thus
can’t modify the original value from the caller. Therefore, the content will
get lost when the method ends and execution flow returns to the caller.
Therefore if you want to modify a string character by character or if you want to access one single character in a string by using an index, you first need to convert the string into an array of characters.

TO BEGIN STEPPING OUT OF THE MANIPULATESTRINGS METHOD

1 Press
Shift+F11
to step out of the ManipulateStrings method, or you can press the
Step Out
button. The application stops abruptly. What just happened is an unhandled exception. An unhandled exception happens whenever an error occurs that is not anticipated or handled explicitly by your application. In that case, the execution of your application is halted because there is no way the application can continue in that state without potentially corrupting the memory or opening security holes. One of the .NET runtime (CLR) principles is to make sure that neither ever happens. Therefore, the CLR crashes your application to prevent your application from continuing to execute in an unknown state. Even though the CLR is taking those precautions, it is less probable to have insecure code executing in .NET, but still possible.

To help you find the bug that raised that unhandled exception, Visual Studio includes
120

Microsoft Visual C# 2005 Express Edition: Build a Program Now!

C07622299.indd 120

C07622299.indd 120

10/24/05 7:13:58 PM

10/24/05 7:13:58 PM

another useful tool: the
Exception Assistant
. This assistant replaces the previous Exception dialog box, and it’s helpful because, based on the context of the exception, it provides more information than before, such as: the type of exception, troubleshooting tips, and corrective actions that may be applied through the Exception Assistant. Look at Figure 7-8 to see what it looks like for the current exception.

When you look at the exception name, the troubleshooting tips, and the data visualizers, it can become apparent why an unhandled exception was raised. The exception name alone is self-explanatory: IndexOutOfRangeException. The first troubleshooting tip displayed asks you to make sure the maximum index on a list

is less than the list size. Arrays in .NET are 0

based; this means that the first element starts

at index 0. The length of the string received as

argument is 10, as shown in Figure 7-8.

The intent of this method was to modify the

last character of the string when the position in

the array is equal to a position passed by value

to the method. In this particular case, the position passed by value to the method is 1. Therefore, in the “for loop” at the second

character of that string, the “if” statement will

return true and then the index
i
will get the

value of the string length. This means that
i
is

now equal to 10. When the application tries to

Figure 7-8

modify the character at index 10, an exception will be generated because index 10 is outside
Exception assistant

of the range of the array. The array has 10 characters with index from 0 to 9. Figure 7-9 uses a new visualizer to look at the char array content.

Figure 7-9

When you move the mouse over program elements,

Array visualizer

you’ll sometimes see a magnifier. If you click the dropdown list, you will see a list of visualizers that display the information in a way that is meaningful to the data

type you’re looking at. For instance, if you’re working

with Extensible Markup Language (XML) or Hypertext

Markup Language (HTML) content, the XML or HTML

Chapter 7: Fixing the Broken Blocks

121

C07622299.indd 121

C07622299.indd 121

10/24/05 7:13:59 PM

10/24/05 7:13:59 PM

visualizer will allow you to see the content as if you were using Microsoft Internet Explorer or any other XML/HTML tool. You’ll use one of the visualizers soon when you debug the ReadFile method.

TO FIX THE OUT OF RANGE PROBLEM

Modify the ManipulateStrings method. Subtract 1 from the string length when you assign a new value 1 to i. The source code should look like this after you modify it:

C A U T I O N

if (i == myPosition)

If at any time you use the Edit and

Continue feature and you see that

{

your data is odd-looking or seems

i = myString.Length - 1;

corrupted, stop the debugging

myTempCharArray[i] = ‘Z’;

process and restart it.

}

After modifying this line of code, move your next execution pointer to the “for” statement so that 2 index i starts at 0. Step through the code or step out. This time there should be no exception. Continue to step through the code; you should now see another message: HelloworlZ. The string has been modified because it was passed by reference.

Continue to step through the code and soon you’ll get a second exception, which is a Division by 0 error. Of course, an exception is raised because the Divide method assigns 0 to the denominator when the numerator is greater than 5. Using a visualizer, you can see that the numerator is 6, therefore 0 will be assigned to the denominator.

Again, the first displayed troubleshooting tip helps by suggesting that you make sure the denominator is not 0. To solve the problem, you could add an “if” statement; but before you do that, consider another .NET principle.

A good practice in .NET is to use the exception mechanism to catch those corner cases instead of coding special conditional instructions which bloat the code. The exceptions are an integral part of the .NET framework and they’re everywhere. Let’s see the logic behind this decision.

122

Microsoft Visual C# 2005 Express Edition: Build a Program Now!

C07622299.indd 122

C07622299.indd 122

10/24/05 7:14:00 PM

10/24/05 7:14:00 PM

In a real application, your application would not purposely assign 0 to the denominator; therefore, most divisions would result in a correct operation. Adding an “If” statement would result in a conditional instruction executed for every single division. And because most divisions would be valid, you would automatically slow down your application. Using an exception-handling mechanism to catch those corner cases is a much better solution because the exception-handling code will get executed only when necessary, so your application should be faster.

When you insert exception-handling code in your application, it is best practice to always catch exceptions from the most precise to the least precise. In this case, you know that the DivisionByZeroException is the one most likely to occur; therefore, it's the first one you want to catch.

When you catch an exception, the exception is “handled.” You then need to do something about it; either you handle it by mentioning it to the user or you throw the exception back. In this case, you want the user to know that an exception was raised but you don’t want the program to crash. Here's an example that demonstrates this form of handling that I'm sure you already know. If you try to divide by zero in Microsoft Office Excel®, Excel won’t crash; it will simply indicate that your entry results in a division by zero and display the

#DIV/0! message in the cell.

An older way of doing things was to make your method return an integer to indicate success or failure. And that’s where people met with trouble because between two applications, and sometimes between two functions, the same integer code meant two different things. You received an integer that was supposed to tell you why your application failed, but the originating code had two meanings, and it was a nightmare to figure out which one was the valid error code. In addition, when people used error codes, their code was ugly because they either had a switch case or a series of nested ifs.

In .NET, you should never design your methods to return an integer to indicate success or failure, nor should you use a Boolean for the same purpose. This is a bad practice that was used when exceptions did not exist or when people didn't know or want to use them appropriately.
You should never do this.
Instead, use exceptions.
Chapter 7: Fixing the Broken Blocks

123

C07622299.indd 123

C07622299.indd 123

10/24/05 7:14:00 PM

10/24/05 7:14:00 PM

TO ADD CODE TO HANDLE DIFFERENT EXCEPTIONS

Click the Stop Debugging button or press Shift+F5 to stop debugging mode. In TestApplication.cs, 1 modify the button1_Click method to look like the following:

Library myObjectLibrary = new Library();

string myString = “Helloworld”;

string myFile = “”;

try

{

MessageBox.Show(myObjectLibrary.Divide(5, 3).ToString());

MessageBox.Show(myObjectLibrary.Divide(3, 3).ToString());

MessageBox.Show(myObjectLibrary.Divide(6, 4).ToString());

}

catch (DivideByZeroException ex)

{

MessageBox.Show(ex.ToString());

}

try

{

myFile = “MyExistingTextFile.txt”;

MessageBox.Show(myObjectLibrary.ReadFile(myFile));

myFile = “MyNotExistingTextFile.txt”;

MessageBox.Show(myObjectLibrary.ReadFile(myFile));

}

catch (FileNotFoundException)

{

MessageBox.Show(myFile + “ doesn’t exist!”);

}

myObjectLibrary.ManipulateStrings(ref myString, 20);

MessageBox.Show(myString);

myObjectLibrary.ManipulateStrings(ref myString, 1);

MessageBox.Show(myString);

Remove all the breakpoints in TestApplication.cs and Library.cs and execute the code. Look at the dif2 ferent message boxes. If a DivideByZeroException or FileNotFoundException occurs, a message box will be displayed.

124

Microsoft Visual C# 2005 Express Edition: Build a Program Now!

Other books

Raunchy by T. Styles
Bones of Empire by William C. Dietz
White Wedding by Milly Johnson
High Plains Massacre by Jon Sharpe
Scene of Crime by Jill McGown
Where Old Ghosts Meet by Kate Evans
Negotiation Tactics by Lori Ryan [romance/suspense]
Cross Channel by Julian Barnes
Reckless Moon by Doreen Owens Malek