Porting Code between Language Implementations

One of the challenges of porting code from one platform to another is that programming languages aren't always standardized, i.e., they may implement features differently, with the result that the same code may not execute the same way on the different platforms.  This means modifications in the code may be necessary.

An example of this is the C++ eof() function, which should return true or false according to whether we have reached the end of file.  That is, we are reading data from a text (ASCII) file, and the eof() function should return

Unfortunately, compilers available to CIS students implement this function differently:

A simple illustration of the difference this makes is shown below.  Suppose we have an input file with a list of numbers, one numeric entry per line, that we wish to total.  Compare how a function to total the file would have to be written for these two implementations of the eof() function.  You might do this by tracing the execution of each version through its processing of a small file (say, with two lines of data).

Borland, Gnu C++ version

void totalFile(char * fName, float & total)
{ fstream rawData;
  float itemPrice;
  total = (float) 0.0;
  rawData.open(fName, ios::in);
  while(!rawData.eof()) {  // (g0)
     rawData >> itemPrice; // (g1)
/* Since the input above might cause us to read past
   the end-of-file, we must check to ensure we don't
   add the last input value a second time. */
     if(!rawData.eof()) // (g2)
        total += itemPrice;  // (g3)
  } // end while
  rawData.close();
} // end echoAndTotal

MS Visual C++ version

void totalFile(char * fName, float & total)
{ fstream rawData;
  float itemPrice;
  total = (float) 0.0;
  rawData.open(fName, ios::in);
  while(!rawData.eof()) {  // (m0)
      rawData >> itemPrice; // (m1)
      total += itemPrice;  // (m2)
  } // end while
  rawData.close();
} // end echoAndTotal

Consider how these execute on a file of two entries, say

5.00
2.56

Both versions initialize total as 0, open the input file, and begin their loops. However, their loops execute somewhat differently in order to produce the same final value of total, as discussed below:

  1. Line (g0) checks that eof is false
  2. Line (g1) reads itemPrice = 5.0
  3. Line (g2) verifies that eof is false
  4. Line (g3) updates total = 5.0
  5. Line (g0) checks that eof is false
  6. Line (g1) reads itemPrice = 2.56
  7. Line (g2) verifies that eof is false, since we haven't yet attempted to read beyond the last data in the file.
  8. Line (g3) updates total = 7.56
  9. Line (g0) verifies that eof is false, as above.
  10. Line (g1) is the attempt to read beyond the end of the data in the file, which makes eof become true.
  11. Therefore, line (g2) decides that control will skip line (g3).
  12. Line (g0) decides that control will exit the while loop.
  1. Line (m0) checks that eof is false
  2. Line (m1) reads itemPrice = 5.0
  3. Line (m2) updates total = 5.0
  4. Line (m0) checks that eof is false
  5. Line (m1) itemPrice = 2.56
  6. Line (m2) updates total = 7.56
  7. Line (m0) checks eof and finds it true, since in this dialect of C++, eof becomes true when we have read the last data in the file.  Hence, line (m0) decides that control will exit the while loop.

Back to Boxer's Home Page