This is an important discussion of Quiz #2 for COM1101,
Winter 2001, Prof. Futrelle's section.

Why?  Because this material will *also* be on the Midterm,
so this is your chance to really learn it and do well on
the Midterm.  There will be additional material on the
Midterm that will be posted for you and gone over in the
review in Monday's class, 2/12/2001.

COME TO THE CLASS FOR THE REVIEW BECAUSE IT WILL NOT EMPHASIZE
THE MATERIAL HERE BUT WILL EMPHASIZE OTHER MATERIAL YOU'LL 
NEED TO KNOW FOR THE MIDTERM. AND READ THE REVIEW NOTES
I'LL BE POSTING.

I CANNOT EMPHASIZE TOO STRONGLY THAT THE PROPER WAY TO 
PREPARE TO WRITE THE ANSWERS TO QUESTIONS ON A TEST IS
TO PRACTICE WRITING OUT CODE ON YOUR OWN AND CHECKING
IT WITH THE BOOK OR BY TRYING TO COMPILE AND RUN WHAT
YOU WRITE.

This message may wrap lines in your mail program, but you can
probably see it better in your browser, where it's at:

http://www.ccs.neu.edu/home/futrelle/teaching/com1101w2001/tests/index.html
   

In the discussions below, I have not distinguished my 
comments from the questions themselves, but when you get your
quizzes back in the morning, you can see which are which.

Here is the grade distribution for Quiz 2: 

100 100 100 100 100 
98 96 96 96 94 93 92 90 90 
88 88 87 87 87 84 84 83 83 80 
77 76 76 75 75 74 74 72 72 71 71 71 70 
68 68 68 68 67 67 65 65 63 62 62 62 
59 59 58 55 54 53 51 50 50 
45 
36 34 34 34 
20

Median is 72 and the mean is 73.4.


  -- RPF

COM 1101 Foundations of Computer Science
Winter 2001 -- Professor Futrelle
College of Computer Science, Northeastern U., Boston, MA

Discussion of results of  Quiz 2 -- given Wednesday, February 7th

(This was the red quiz.)

Question 1:

Below is a set of items of code, "scrambled" -- not in their
original order. You are to assign each item to one of three file
types: The Interface File, the Implementation File or the
Application File. Make three lists of items, one for each file
type. List the numbers (only the numbers!) in the order that they
should appear in each file (when the order is important) e.g.,
something that looks like this but with the numbers in the right
places.

 Interface File -- has prototypes and Class ADTs w. prototypes
 
   2 and 4
 
 Implementation File -- has definitions  
 
   3 and 5
  
 Application File -- has the "application", the main() program that runs
 
   1

Here are the code items: 

     1.      int andMoreFun(){ return 7;}    

     2.      int andMoreFun();

     3.      void main(){fun(); cout << andMoreFun() << " times more fun!";}

     4.      void fun();

     5.      void fun(){cout << "A bit of fun or " << endl;}

Many got the pairings right but the names of the files mixed up.
I was not harsh in grading if you got them grouped correctly, since
this was partly a terminology issue.

When the above code is properly organized, compiled and run, 
what does it print out? 

A bit more fun or
7 times more fun!

Note that there's an endl after "or" -- many forgot this.

 

Question 2:

     1. Write the prototype for a void function myTruck() of one argument where 
     the argument is an array of objects of class Truck. 
     (You needn't define the class and note that myTruck() is not a 
     member function of the class.) 
     
     2. Write the definition of myTruck() such that it prints the year field of the 
     truck at array element 9.
      
     3. Write an example of a call to the function myTruck(), passing it an array of 
     Truck objects, held in the variable: Truck myTruckArray[30]. 

  
2.1  A prototype must have no body and the return type and the 
types of each argument must be specified. 
So the prototype of myTruck() must be,

    void myTruck(Truck []);  or it can be void myTruck(Truck tr[]);
    
It is not correct to omit the argument type.  Some put int as the
type, but the type specified was Truck.  Some put in the size of
the array, 30.  That's wrong, since such functions take arrays of
any length.  A few involved the prototype in a class definition,
but it was stated that myTruck() was not a member function.

2.2 The definition must have the same return type and the same
argument types as the prototype.  First, it says that the
function prints something, so it must have a cout << .... in it. 
Second it says what it is to print.  For the 9th element of the
array it is to print the year field.  Now the 9th element of an
array of Trucks is a Truck object (not a class, but an object, a
particular instance, with its own value of year).  So here's a
correct definition:

  void myTruck(Truck tr[]) {
  
  		cout << tr[9].year ;
   
   ]
  
That is, tr[9] is a Truck object and you access the field of any
object with the dot operator (unless it is a pointer to an object
-- not considered in this quiz). It is never correct to include a
class name before a dot operator.  Only a class instance or
object. For example, if we had a collection of Car objects each 
with different speeds, it would make no sense to write Car.speed 
-- which car would that be for?

2.3  As I and the book have emphasized, passing an entire array
to a function is a simple process.  The call is simply written
as,

   myTruck(myTruckArray);
   
Note that no [] is used and the dimensions are certainly not
used.  All the function is getting is the location of the
beginning of the array.  Trying to pass the function an argument
such as myTruckArray[30] would have two problems: It wouldn't
compile because the argument type would be wrong. 
There could be functions that take a single Truck object as
an argument, but even then, myTruckArray[30] would not be
a proper Truck object, since the array indeces only go from
0 through 29.
 

Question 3:

Here is the API specification for a Rectangle class: 

// sets the dimensions of the rectangle
 void setDimensions(double length, double width); 
 
 // returns the length of the rectangle
 double getLength();

Write an ADT for the class that has only the private member
variables width and area, both of type double, as well as the two
public member functions.

Write definitions for the member functions setDimensions() and
getLength() where the former behaves as if it is setting the
dimensions, as evidence by the latter function that returns the
value of the length. That is, the class behaves externally as if
it contains the length and width, but only stores the area and
width.

Note that the member variables are not in the API, since they're
not accessible, they're private.  But writing out the ADT for the 
class means giving the class definition but without the
definitions for the member functions, only their protoypes.

So here's the ADT for the Rectangle class.  Happily, most students
got this right.  That's very good.

class Rectangle {

	public:  // copied from above
	
	void setDimensions(double length, double width);

    double getLength();
    
    private:
    
    double width, area;
    
};  // most got this semicolon right

The problems began with the definitions of the functions.

In *abstract data type*, the internal representation does not have
to be the same as what's accessible outside the class.  In this
case each object of type Rectangle can only store the value of the
width and area.  But of course the length can be returned simply
by returning the quotient area/width, since area = length*width,
as practically everyone (but not everyone!) realized.

PROBABLY THE BIGGEST DIFFICULTY THAT EVERYONE HAD WITH THIS PROBLEM
IS THAT MANY SEEMED TO THINK THAT VALUES ARE ALWAYS GOTTEN FROM
THE USER.  THAT'S RARELY THE CASE IN REAL SYSTEMS!  IF YOU RUN
THE DATE FUNCTION IN UNIX, IT USES AS ITS ARGUMENT THE TIME IT
GETS FROM THE SYSTEM AND THEN FORMATS IT AS A DATE AND TIME AND
PRINTS IT OUT.  IT WOULD BE ABSURD FOR IT TO ASK YOU FOR THE
TIME; YOU'RE ASKING IT!  SIMILARLY IF A WEB SERVER IS RUNNING A
PROGRAM TO TELL YOU IF SOMETHING IS IN STOCK AT A STORE, IT
DOESN'T GET ITS INPUT FROM YOU OR EVEN FROM AN EMPLOYEE, IT GETS
IT FROM A DATABASE THAT RECORDS WHAT'S IN STOCK. STUDENTS ARE SO
USED TO INTERACTING WITH SYSTEMS THAT THEY DON'T REALIZE THAT 99%
OF WHAT GOES ON INSIDE SYSTEMS IS THAT THE VARIOUS FUNCTIONS
INSIDE THE SYSTEM CALL ONE ANOTHER GIVING THE FUNCTIONS VALUES
THEY GENERATE, NOT GET FROM YOU THE USER.  AS ANOTHER EXAMPLE,
IN MY CAR SIMULATION PROGRAM THERE IS NOT ONE SINGLE cin >>
STATEMENT.  I SIMPLY PUT THE VALUES I WANT TO USE AS VALUES
OF VARIABLES IN THE PROGRAM BEFORE I COMPILE IT AND THEN IT
USES THOSE VALUES IN CALLS TO FUNCTIONS AND THOSE FUNCTIONS
MAY CALL STILL OTHERS.  AT NO TIME DOES IT GET INPUT FROM
ME, ONCE THE PROGRAM RUNS.  THE FUNCTION IN MY PROGRAM ACCEPT
AND RETURN VARIOUS VALUES WHILE IT RUNS, BUT IT NEVER REQUESTS
ANY INPUT FROM ME AND THE ONLY OUTPUT IT EVER PRODUCES ARE
SOME POSITIONALLY LAID OUT CHARACTERS.

So below are proper definitions of the functions, and none of them
do, or should(!), get any input from the user:

The setDimensions() function is to set the values inside any
Rectangle object (instance) given the values passed to it as
arguments.  Since only the length and width are passed to the
function and only the width and area are stored internally, a
tiny bit of computation is required. Furthermore, the name of the
arguments should NOT be the same as the names of the member
variables.  That produces name clashes.  The majority of you just
used the same names. If you tried this, the member variable would
never get set, only the local variable named as the argument.

Defintion:

void Rectangle::setDimensions(double lengthArg, double widthArg){

	width = widthArg;
	area = width * lengthArg; // so now the object has all it needs
}

Some people had the function above return a value. 
A void function cannot have a return statement.
Here's a use of the function above:

Rectangle r;
r.setDimensions(standardLength*2.0, standardWidth - 4.0);

Many people tried to introduce a length variable in the function
setDimensions, but of course there's no length member variable 
in the class Rectangle, so this would accomplish nothing.

But in the function getLength(), the result is to be returned
to whatever program calls the function.

Definition:

double Rectangle::getLength(){
    
    return area/width;  // no need to define a local variable length  
}

Here's a typical use of the function above:

Rectangle rr;
initialize(rr);
if(rr.getLength()) > maxLength)   
   { rr.storeInFile(rectFile); }
   
Note that nothing is asked of the user and nothing is printed.
In the example above, the returned value is compared to maxLength
and then discarded.

RETURNING A VALUE DOES NOT MEAN PRINTING IT!  When the
sqrt() function returns a value, e.g.,  a = sqrt(25), it does not
print anything. There is no print statement *inside* the sqrt()
function and you should not generally put any print statement
inside a function that returns a value.  You simply use return
and let the program that uses the value returned decide what to
do with it. Whether you choose to print the value the sqrt
returns or not depends on what you are using it for.

BOTTOM LINE:  SETTING A VALUE ALMOST NEVER MEANS ASKING THE USER
FOR A VALUE AND RETURNING A VALUE ALMOST NEVER MEANS PRINTING IT.
IF YOU EVER THINK YOU NEED TO DO THIS, THINK AGAIN! 

THERE ARE COMPUTER SCIENCE TEACHERS WHO INSIST THAT THEIR STUDENTS
WRITE SOME PROGRAMS WITHOUT ANY USER INPUT OR OUTPUT AT ALL. 

A HUGE SIMULATION PROGRAM FOR SIMULATING A NEW AIRPLANE DESIGN
MAY RUN FOR 30 HOURS ON A SUPERCOMPUTER AND PASS ARGUMENT VALUES
AND RECEIVE BACK RETURN VALUES FROM MANY BILLIONS OF
COMPUTATIONS, ONLY GIVING A TINY FRACTION OF ITS VALUES AS OUTPUT
FOR USERS TO LOOK AT. IF EVERY FUNCTION IN THE SIMULATION THAT
RETURNED A VALUE PRINTED, IT COULD EASILY USE UP THE WORLD'S
SUPPLY OF PAPER IN A FEW DAYS OR WOULD WRITE BILLIONS OF LINES
OF OUTPUT TO A SCREEN.  WHO COULD READ THAT?!