CIS-255 Home http://www.c-jump.com/bcc/c255c/c255syllabus.htm
This handout outlines the steps that I took to get started on the IntStack assignment.
The demo code I wrote in class is posted on the CIS-255 C++ Samples page. You can download sample files, start a new project, and add
IntStack_4_beginners_main.cpp
IntStack.cpp
files to your project's source files.
Below is a brief outline of steps that I took to write this demo.
Initially, I wrote a small main program, pretending that I already have a working stack object:
// main.cpp #include "IntStack.h" int main() { IntStack st; st.reset(); int x = 999; st.push( x ); int y; y = st.top(); st.pop(); return 0; }
To make this functional, we need to define what "IntStack" is.
Defining "IntStack" is the job of IntStack.h.
In IntStack.h file we have a class that behaves like a stack of integers. (Please note that I wrote this without looking at the actual assignment document; you might want to double check if all function parameters and return types agree with the assignment requirements.)
// IntStack.h class IntStack { public: static const int STACK_SIZE = 100; private: int m_array[ STACK_SIZE ]; unsigned int m_sp; public: // public interface of the stack: void push( int element ); int top(); void pop(); unsigned int size(); void reset(); };//class IntStack
What you see here is the C++ header file, not the source file.
Header files don't have any executable code.
Header files declare constants, variables, classes, and functions, but do not contain any actual code that is typically found inside function bodies.
So far the class IntStack has only data members and a few member function declarations.
Therefore, the bodies of member functions must be defined elsewhere.
Because IntStack could be useful in other projects, it's worth creating a separate implementation file and write member function definitions in that file.
I named my file IntStack.cpp:
// IntStack.cpp
#include <iostream> // needed for std::cerr
#include "IntStack.h"
void IntStack::reset()
{
m_sp = 0;
}
void IntStack::push( int element )
{
// before:
// [] [] [] [] [] []
// |
// m_sp
//
// after:
// [] [] [e] [] [] []
// |
// m_sp
//
m_array[ m_sp ] = element;
++m_sp;
}
int IntStack::top()
{
if ( m_sp == 0 ) {
std::cerr << "stack is empty!";
return -1;
}
return m_array[ m_sp - 1 ];
}
void IntStack::pop()
{
// Not implemented
}
unsigned int IntStack::size()
{
return m_sp;
}
Note that I didn't implement all of it, only push, top, and size.
The above file, IntStack.cpp is a C++ source file, also known as C++ implementation file.
This means that is is compiled separately from the file that contains the main( ) function.
The linker makes executable image of the program by combining the results of the two source files in my project.
Notice that my version of push never checks if the stack is full (apparently, when m_sp == STACK_SIZE.) So you should add this check to the code yourself.
Also, std::cerr is very much like std::cout and represents the standard output stream for errors
std::cerr should be used when you need to print the information about errors.
As other stream objects, std::cerr comes from iostream standard library header:
// IntStack.cpp #include <iostream> // ...
One final note that each function name is prefixed by IntStack::
// IntStack.cpp
// ...
void IntStack::push( int element )
{
//...
}
This is because our functions come from the scope of class IntStack. In other words, these funtions are not part of the global scope. The only function declared in global scope is the main entry into our program. The two-colon operator " :: " is the scope resolution operator.