CS170 Lab: Introduction to Visual Studio

Highlights of this lab:

The purpose of this lab is to introduce the Microsoft Visual Studio programming environment for C++. All of the C++ programming concepts are the same as you've seen all semester, it is merely the environment that is new here. Visual Studio provides an IDE, an Integrated Design Environment that simplifies program development and debugging. This is the environment that is used in the CS210 class.

Lab Exercise:

1. C++ Classes

1.1 Classes

Function definitions are usually put in separate files in C++.

We split the program into two files, a header file (which we give the extension .h) and a program file (which we give the extension .cpp). The header file contains the class declarations for one or more classes, and the program file contains method definitions. The program file includes the header so that it knows about the declarations.

The scope operator :: is used when declaring methods. If I have a class called Foo and it has a method called myMethod, when defining the function in the .cpp file, I would call it Foo::myMethod. The scope operator is needed because a .cpp file could contain method definitions for multiple classes, so we need to know for which class each method is being defined. In the example class below, we add a myMethod member function, and you can see the scope operator in use. A main function is also provided so you can run this program.

Foo.h

class Foo {
public:
    Foo();
    Foo(int a); // second constructor
    ~Foo();
    int myMethod(int a, int b);
};  // note the semicolon after the class declaration!

Foo.cpp

#include "Foo.h"

Foo::Foo()  // scope operator :: helps define constructor for class Foo
{
    cout << "I am a happy constructor" << endl;
    _num = 5;
}

Foo::Foo(int a)
{
	cout << "Calling the second constructor." << endl;
	_num = a;
}

Foo::~Foo()
{
    cout << "I am a happy destructor that would do cleanup here." << endl;
}

int Foo::myMethod(int a, int b)
{
    return a + b + _num;
}

main.cpp

#include "Foo.h"
int main()
{
	int i;
	Foo foo, foo1(9);
	 
	i = foo.myMethod(10, 11); //call foo's myMethod()
	cout << " i is : " << i << endl;

	i = foo1.myMethod(10, 11); // call foo1's myMethod()
	cout << " i is : " << i << endl;

	return 0;
}

It's crucial that you remember the semicolon at the end of a C++ class declaration. Failure to include the semicolon will cause a compile-time error, but not at the end of the class declaration. Often the error will be reported in a perfectly viable file, such as in a header file that you included.

1.2 Protection

There are 3 levels of protection for class members in C++: public, private, and protected. Protected members are only accessible to subclasses. As you've probably noticed, you put members in sections by their protection level. You can have as many sections of each protection level in a class declarations as you would like. If no modifier is specified, the protection level defaults to private.

C++ also has an additional form of control over protection levels called friendship that allows for a finer grain of protection.  To find out more, consult your text books.

1.3 Inlining

Methods can be declared and defined in the same place by defining methods in the header file. This is known in C++ as inlining. Inlining is typically used only for very short methods such as accessors and mutators. For short routines, C++ can frequently optimize things which are declared inline by inserting the code for the routine directly in the calling function, thus avoiding the large overhead of calling a function. So, it is often to your advantage to inline definitions of accessors, mutators, and other short, frequently called functions that don't require use of an external library.

//Color.h
class Color
{
public:
   Color();
   int getRed() {return _red;}       // inline declaration
   void setRed(int red) {_red=red;}  // inline declaration
   /* same for green and blue */
protected:
   int _red, _green, _blue;
};

Note that medium and large-sized functions should not be inlined, even if they are frequently used. Since the the compiler will insert the code for inlined functions wherever the function is called, inlining large functions will increase the size of your program, possibly slowing it down.

2. Visual Studio C++

 

The Visual C++ package contains more than a compiler; it also contains all the libraries, examples, and documentation needed to create applications for Windows 95, 98 and Windows NT.

2.1 Creating Your First C++ Program

A console mode application is a character based program that runs in a DOS window.

For your first C++ program, you will build a console mode application that displays a greeting message. This (i.e. a console mode application)is the kind of VC++ programs that you will build for all your lab and class exercises/assignments. 

Console mode programs are often simpler to build than Windows applications, and this example will take you through the steps of creating, building and executing a program in Visual C++. We first assume that you use the built-in code editor in Visual Studio to edit your code; then we will show you how to build and run your C++ programs that you have created with any external editors. 

2.1.1 How to start

Press  on your window desktop, choose Microsoft Visual Studio 6.0 from the popup menu, then choose Microsoft Visual C++.

The following figure shows different areas of a Visual Studio work window.
 

2.1.2 Starting Your First Program

Before you create your program in C++, you need to create a work space for it.  This work space will hold all the files that are parts of your program, including the C++ source code, the header files, etc.  To create a new work space, click on File from the Microsoft Visual C++ window (see above figure) and select New.  Choose from the project list.  Type in a project name and select a directory for this project:

After this, click on OK to go to the next screen.  Do not worry about the options in the next screen; simple click Finish and then OK and a work space for your first VC++ project is created.  

Next, you would type in your C++ source code.

Select File-->New from the main menu, and select C++ Source File from the New dialog box under the Files tab.  Type in the file name: hello.cpp under the "File name".  This file will be added to the hello work space that we have just created, and a blank document will be opened for editing

Exercise:

Type in the following program in the source code editor:

// FILE:     hello.cpp
// PURPOSE:  An example for simple I/O steam 

#include <iostream.h>
main()
{
	char name[50];
	cout << "Please enter your name:" << endl;
	
	cin >> name;
	cout << "Hello, " << name << endl;
	return 0;
}

Save your file after you have finished editing it.

2.1.3 Building the hello Project

In order to compile any code in Visual C++, you have to create a project. A project holds three different types of information:

1) It remembers all of the source code files that combine together to create one executable. In this simple example, the file hello.cpp will  be the only source file, but in larger applications you often break the code up into several different files to make it easier to understand (and  also to make it possible for several people to work on it  simultaneously). The project maintains a list of the different source files and compiles all of them as necessary each time you want to create a  new executable. 

2) It remembers compiler and linker options particular to this specific application. For example, it remembers which libraries to link into the executable, whether or not you want to use pre-compiled headers, and so on.

3) It remembers what type of project you wish to build: a console application, a windows application, etc.

If you are familiar with makefiles, then it is easy to think of a project as a machine-generated makefile that has a very easy-to-understand user interface to manipulate it. For now we will create a very simple project file and use it to compile hello.cpp.

Exercise:

1. Compile the hello project by selecting Build --> Compile hello.cpp from the main menu.
It simply compiles the source file and forms the object file (hello.obj) for it. It does not perform a link, so it is useful only for quickly compiling a file to check for errors.

2. Select Build -->Build hello.exe from the menu bar to link the program.
It compiles all of the source files in the project that have been modified since the last build, and then links them to create an executable.

3. Choose Build --> to run the program. A DOS window will popup.

If errors or warnings are displayed in the Build status window, there is probably an error in the source file. Check your source file again for missing semicolons, quotes, or braces.

2.2 How to compile, link and execute a program with multiple files?

The above section shows the procedure of creating a C++ program with only one file component: hello.cpp, and we used the build-in VC++ source code editor to edit the file.  However, when you are working on a large program, you would break your program into smaller, more manageable parts.  In other words, your project would contain more than one C++ source files.  Moreover, you might not have used the VC++ source code editor to edit your files.

The following section demonstrates how to create, compile, and execute  a VC++ project with more than one file.

Exercise:

2.2.1 Ftp multiple files from pub/class/170/ftp/cpp to C:\workarea.

Double click the icon on the windows desktop then click OK on the resultant window:
Next, double click the green up arrrow in the window similar to the following:
Then double click on the following folder icons  ( 170 folder / ftp folder / cpp folder).
Make sure your local system is C:\Workarea and ASCII is being selected.
While holding down the Ctrl key, select date.h (header file), date.cpp and main.cpp then press .

Once the files are transferred to the local System, click exit to quit the ftp program.

2.2.2 Creating a  Microsoft visual C++ work space

Step 1.   Select File --> New.
Step 2.   Select Win32 Console Application.
Step 3.   Set the project location to C:\Workarea.
Step 4.   Set the project name to lab1.
Step 5.   Select OK to create the project.
Step 6.   Select an empty project, click finish and click OK.

Once the project is created, you add files to the project, as follows:

1.Select Project --> Add to Project --> Files.
2.Choose C:\Workarea, highlight the .h and .cpp files in the project: date.cpp, date.h and main.cpp
3.Select OK to add the files to the project.

2.2.3 Compile, build and execute your progam

1. Select Build  --> Build lab1.exe (This will compile and link the files).
2. Select Build --> Execute lab1.exe.

 

3. Debugging C++ Programs

"To err is human...", so Alexander Pope said.  And if he were living at the present time, Pope might as well be commenting on the process of programming. If you are like most of the people, your program will not work as you expect the first time you build them.  This is true even with the simplest programs.  Therefore, debugging is a very important process in programming; sometimes it is even more time-consuming than writing the program.

Visual Studio comes with a very powerful debugging utility which helps you locating programming errors.  It is very important to keep in mind that in order to use the debugger in VC++, your program should compile with no errors.  In other words, debugger can only help you spot runtime errors. 

In the following, we briefly introduce some common commands in the debugger, and then take you through the debugging of a sample program.

To start the debugger, a project must be open in the development environment. Once you have opened the project you wish to debug, the debugger is invoked by choosing any of the debug commands. The debug commands are located in the "Build" menu under the sub-heading "Start Debug." You can access several other debug commands, in addition to those in the menu, from the debug toolbar, which is displayed by selecting "customize" from the "Tools" menu. This toolbar is displayed automatically when you invoke the debugger. Some of the more common commands are listed below:

3.1 Useful commands

  • Setting breakpoint  A breakpoint is any point in the executable code where the execution stops, allowing the programmer to see what is going on inside the program as it runs. Breakpoints allow you to run through portions of the code where there are no problems, so that you can spend your time focusing on the areas that need to be fixed.

    Setting a breakpoint is easy. Place the cursor on the line of source code you want to stop on. Then from the toolbar, select the hand icon: Breakpoint icon. You may also set a breakpoint by right-clicking the mouse and selecting "Insert/Remove Breakpoint" from the pop-up menu. A red dot will appear in the gray bar to the left of the line of code to indicate the breakpoint has been set. If you press the hand icon a second time, the breakpoint will be removed and the dot will disappear.

    Go   This command can be found by clicking on Build | Start Debug  and then select Go.  There is also a shortcut in the menu bar: The Go command executes code from the current location until it reaches a breakpoint, the end of the program, or a point at which the program pauses to get input from the user.

    Step Into   When Step Into is chosen, the debugger executes each C++ statement one by one. Pausing to let the programmer check the values of variables or make adjustments between statements. Step Into lets the programmer step into every function call, loop, or other code block in the program. In essence, no statement will be executed until the programmer is ready to execute it.

    Step Out   Step Out is used in conjunction with Step Into. It will immediately execute the remaining code in the current function call, loop, or other code block, then pause execution. The programmer can continue to debug the program.

    Step Over   This command is used to step through a program without stepping into function calls. When Step Over is used on a function call, loop, or other code block, the entire block is executed immediately.

    Run to Cursor   Run to Cursor executes the program up to the point in the code where the cursor is located. Then execution is paused.

     

  • 3.2 Debugging a sample program

    Here is the sample program (debug.cpp) we would like to debug:

    ////////////////////////////////////////////////////////////////////////
    // This program reads five numbers from the keyboard, print out 
    // these five numbers on the screen, and then prints out the 
    // average and the maximum value
    //
    ///////////////////////////////////////////////////////////////////////
    #include <iostream>
    using namespace std;
    
    // Global Constants
    
    const int MAX = 5 ;
    
    // Function Prototypes
    
    double GetAverage( const int IntArray[], const int Max) ;
    
    int GetMax( const int IntArray[], const int Max ) ;
    
    
    int main() 
    {
       int Values[MAX] ;
       int Count ;
    
       cout << "Enter five numbers: " << endl ;
    
       // First we read in the numbers.
       for (Count = 0; Count < MAX ; Count++ ){
           cout << "Enter the next number : " ;
           cin >> Values[1] ;
       }
    
    
       // Now we echo the input back to the user
       for ( Count = 1; Count < MAX ; Count++){
            cout << "Value [ " << Count << "] is : " << Values[Count] << endl ;
       }
    
       // Now lets call a function to get the average:
       cout << "The average is " << GetAverage(Values, MAX ) << endl ;
    
       // Finally we can get the maximum value
       cout << "The Maximum value is : " << GetMax(Values, MAX) << endl ;
    
       return 0 ;
    
    } // End of Main
    
    
    double GetAverage(const int IntArray[], int Max)
    {
      double temp = 0.0 ;
      for ( int i = 0 ; i < Max; i++) 
          temp += IntArray[i] ;
    
      temp /= Max ;
      return temp ;
    } // End of GetAverage
    
    
    int GetMax( const int IntArray[], const int Max)
    {
       int Biggest = IntArray[0] ;
    
       for ( int i = 1; i < Max; i++)
          if (Biggest > IntArray[i])
               Biggest = IntArray[i] ;
    
      return Biggest ;
    } // End of GetMax()

    Following these steps to debug this program:

    1) Set up a project for this program (follow the same procedure as discussed in section 2 of this lab.).  Name this project debug.

    2) Compile and link the code after entering the code.  If there is any compiler error or linker errors, correct them (Remember, your program should pass the compilation before you can use the debugger).  However, if you spot any logical errors in this program, DO NOT correct them at this point.

    3) Run the program as usual to see how it works. Do not use the debugger yet.  Enter 1, 2, 3, 4, 5 as the input.  The first thing you will notice is that the five numbers printed out by the program are not the same numbers that you have just entered.  Therefore, something is wrong with the program.  We will use the debugger to find out what is wrong.

    4)  Set up a break point. As we mentioned earlier, a breakpoint is any point in the executable code where the execution stops. A breakpoint pauses the execution of a program so that the programmer can take a look at what is going on inside the program when it runs. At this point, we do not know what caused the program to go wrong, so we set up a breakpoint after the first cout statement. To do this, place the cursor before the statement which runs right after the cout statement and click on the icon. A red dot will appear besides the cursor position. See the following figure:

    Now we need to RUN the code with debugging. Select Build | Start Debug | Go from the menu or press this icon on the menu bar: Go icon.(DO NOT USE "Execute Program" (the Exclamation Point on the toolbar: ; this runs the program, but without any debugging information).  The program will start to execute, then stop at the breakpoint. Notice that the output window comes up, but there is nothing in it. The VC++ work windows have changed, now showing the source code window across the top, an immediate watch window on the bottom left, and a watch window on the right. A yellow arrow has appeared on the red dot to the breakpoint, indicating the current line of code being executed.  (See the following figure:)

    Next, we will look at some of the variables.

    5) Use watch windows to trace the values of variables.  There are two kinds of watch windows in VC++ environment: the immediate watch window  and watch window, as is illustrated in the above figure. The watch windows enable the programmer to watch the state of the variables as the program executes, and thus to see if the program is doing what was intended.

    Immediate Watch Window: Displays variables that are of immediate interest. For example, after we set up a break point right before the first for statement, two variables appear in the immediate watch window: Count and Values. Although there are more than two variables in the program, these are the two variables that are of immediate interest. Notice that there is a small plus in a box to the left of the variable Values, and its value looks like this: 0x006bfde4:  

    The 0x indicates that it is a hexidecimal value. Since Values is an array of integers, the value being displayed is the memory location where the array begins. Click on the plus sign on the left of the variable name. The array expands below the name, showing the indices of the array and the values for each of the integers in the array. The plus sign has also become a minus sign. Click on the minus sign to hide the array.

    Watch Window: This watch window becomes useful when you would like to watch any variables in your program at all times, regardless if it is being watched by the immediate window or not.  To watch a variable (or an expression) in this window, simply select a variable from the immediate watch window and "drag" it into the Watch Window, or type the name of the variable or expression that you would like to watch in the Watch Window.  In our example, we would like to watch Count and Values at all times, (since the values of Values are not printed out correctly on the screen when we run the program in step 2)), so we drag these two variables into this watch window.

    6) Stepping through the code.   VC++ programming environment allows you to step through the code in two different ways.  You can a) execute one line at a time, stepping into each function call, or b) run the function without tracing what is going on inside the function.  We will look at examples of the first.

    Right now, the execution of your program halts after the first cout statement is executed, because we set a breakpoint there.  This is indicated by a yellow arrow inside the red dot: . Let's step into the loop and see what happens.

    On the Tool bar are four icons showing braces. If you don't see this toolbar, go to Tools->Customize... and click on the check-box for Debug. One Debug icon shows a blue arrow jumping over the braces (Step Over F10) Step Over Icon. Another shows the arrow pointing into the braces (Step Into F11) Step Into Icon. These are the buttons for single stepping through a program. The other two buttons are the Step Out and Run to Cursor. These allow you to skip large blocks of code in debugging. We'll leave these two functions for you to explore on your own. Let's use the Step Over Button first.

    Press the Step Over button .  The yellow arrow will move to the next line.  Keep pressing the Step Over button until the yellow button is pointing at the beginning of the cin  statement and the debugger dialog window is greyed out:

    From the bottom of the Windows desktop, click on the Dos icon to maximize the Dos window , because at this point, the program is expecting some input from the user. enter the number 1 as the input and hit return.

    Now click on the plus sign to the left of  the variable Values in the Watch Window to expand that variable.  We notice that something is wrong here: the first number we entered just now should be assigned to Values[0], but instead, it is assigned to Values[1]:

    Examine the code in the source code window, and you will find that inside the first loop block, the statement   cin << Values[1]; should read: cin << Values[Count];; otherwise, all the keyboard input will go to Values[1]. Go to the Debug menu and select Stop Debugging to quit the debugger. Change that line of code; recompile and rerun the program and it should work properly.

    Note: You can enter CTRL + Shift + F9 to remove all breakpoints.
    To remove just one breakpoint, click on the line of code containing the breakpoint, and click on the hand icon. This will toggle the breakpoint on/off.

    We leave it to you to explore other features of the VC++ debugging utility.

    3.3 Getting into trouble

    In the above example, we used the Step Over to examine the loop.  What will happen if we use Step In? As we mentioned above, Step In will examine the program one line a time and it will go into every function if a function is called.  Therefore, if we use Step In to examine the above loop, we would have stepped into the  cout and cin system functions. this is not what we want. So when you debug your program, whenever you encounter the system functions, which do not need to be debugged, use Step Over instead of Step In. 

    This is one of the tricky part of the debugging process which could get you into trouble.  You will get into even more troubles if you do not know what you are doing.  The following are some surprises, how they happened, and how to deal with them.

    Problem one: The MS-DOS console window disappears quickly after it appears.  

    The window is still there. You'll find it from the bottom of your desktop.

    Problem two:  A "Find File" dialog box pops up.  

    You probably pressed Step Into when you should have pressed over , and you entered some function you didn't expect (such as a predefined library function). This might happen especially if you press Step Into when the arrow points to an input or output statement (the << and >> operators are actually predefined functions). (It can also happen if you press Step Over  beyond the point where your program ends.) VC++ is asking for a file containing the source code for this function. Select Debug/Step Out) to finish executing the library function and get execution back to your source code.

    Problem three:  My source code has been replaced with weird stuff, with numbers in the left-hand column and words like "push" and "mov."  

    This happens for the same reasons as above: you probably entered a library function with (should have used ). This is the assembly code version of the function. Select File | Close to get back to your source code window,  then press to finish executing the library function and get execution back to your source code.

    If all else fails, you can always select Debug | Restart to start your program over again, or select Debug | Stop Debugging to quit execution of your program and stop debugging altogether.


     

    4. Recursive Function Shown via the Debugger

    If you have a look at any C++ text, you will see an explanation of a recursive function. These explanations will all tell you that a recursive function is one that calls itself repeatedly until some base condition is reached. An example given in one book compares the process to opening a set of Russian Matroishka dolls until you get to the smallest solid doll contained in the set. When you get to that last case, you start putting the doll back together again.

    The point is, that you keep going until you get to some predefined base condition.

    Consider the following example of a simple recursive function:

    //    Filename: 170Power.cpp
    //
    //    Purpose: To illustrate a recursive function.
    //             Call the function with a value and a power.
    //             Base condition is when power value = 1.
    
    #include <iostream>
    using namespace std;
    
    int PowerFunction(int, int);
    
    int main()
    {
        int Value;
        int PowerValue;
    
        cout << endl << "This program raises a number to a given power."
             << endl << "Enter number value, and power: ";
        cin >> Value >> PowerValue;
    
        cout << endl << "The result is: "
             << PowerFunction(Value, PowerValue)
    		 << endl;
        return 0;
    }
    
    
    int PowerFunction(int p_Value, int p_PowerValue)
    
    {
        if (p_PowerValue == 1)      // Base condition
    
            return p_Value;
        else
            return p_Value * PowerFunction(p_Value, p_PowerValue -1);
    }
    

    Let's go through the steps you'd need to use in the Visual C++ environment to create that program and run it under the debugger.

    1. Start Visual Studio C++.

    2. Select File -> New.
      • Win32 Console Application.
      • Project Name: 170Power
      • Location: C:\Workarea\170Power
      • OK
      • Finish
      • OK.

    3. Select File -> New.
      • C++ Source File
      • Filename: 170Power.cpp

    4. Use your mouse to select the source code from this web page and paste it into the Visual C++ Edit area.

    5. Save the file in Visual C++.

    6. Build -> Compile to compile the program.

    7. Build -> Build 170Power.exe to run the program.
      Run the program with the values 2 and 3, and you should get a result of 8.

    8. Now, run the program with the debugger so you can see what's happening.
      Set a breakpoint on the Base Condition in the recursive function. i.e. if (p_PowerValue == 1)
      Remember, to set a breakpoint, click on the line of code, and then click on the little hand. Breakpoint icon A red dot should appear beside the line of code you've just selected.

    9. Build -> Start Debug -> Go to run with the debugger.

    10. After you enter the values 2 and 3, you should observe the values of p_PowerValue and p_Value as you execute the function by continually clicking on the Step Into button.

    11. Note: If you click on the StepInto button too many times, you get into some strange looking code in the Edit area. Just double-click 170Power.cpp in the FileView window at the left to get back to your program.

    The original text for this page was created by Qiang Hu.

    This page last modified:
    Monday, 18-Jun-2012 14:21:25 CST
    Accessed     times.

    CS Dept Home Page
    CS Dept Class Files
    CS170 Class Files


    Copyright: Department of Computer Science, University of Regina.