[comp.lang.ada] END_ERROR on Text_Io.Get

ylarotiala@cc.helsinki.fi (03/02/89)

   I wrote a piece of code:
      
   WHILE NOT Text_Io.End_Of_File(File) LOOP
   	Text_Io.Get(File,C);
   	...
   END LOOP;
   
   I believed that this would just read the File  character  by  character
   but I was wrong. Tests gave results:
   
   1) A file with two lines, text on both
   >first line<EOLN>
   >second line<EOF>
   
   Everything  is  just fine; my program sees the file, reads it and finds
   the end of it.
   
   2) A file with three lines, the third beign empty
   >first line<EOLN>
   >second line<EOLN>
   ><EOF>
   
   This   time   Text_Io.Get  raises  END_ERROR.  LRM(14.3.4)  says  about
   END_OF_FILE:

   "Returns  TRUE  if  file terminator is next, or if the combination of a
   line, a page, and a file terminator is next; otherwise returns  FALSE."

   Does  this  mean that the combination "line and file terminator" is not
   detected? Why is the exception raised?
   
   A. Yl{-Rotiala
   ylarotiala @cc.helsinki.fi	- Helsinki, Finland
   

gvcormack@watdragon.waterloo.edu (Gordon V. Cormack) (03/05/89)

In article <2445@cc.helsinki.fi>, ylarotiala@cc.helsinki.fi writes:
> 
>    I wrote a piece of code:
>       
>    WHILE NOT Text_Io.End_Of_File(File) LOOP
>    	Text_Io.Get(File,C);
>    	...
>    END LOOP;

Get(char) ignores end-of-line, but End_of_file doesn't.  I don't like
the definition, but that's the way it is.  Any function like End_of_file
which trys to predict the future is destined to be strange.  I'm not
sure why Ada copied Pascal in this regard.  In Pascal it was sort of
necessary to compensate for the lack of a proper loop construct, but
I see no excuse in Ada.

It is necessary to get rid of newlines before END_OF_FILE will work
properly in this case.  Here is a sample program that echos its 
input (ignoring newlines).


with text_io; use text_io;
procedure eof is
   x: character;
begin
   loop
      while end_of_line and then not end_of_file loop
         skip_line;   -- get rid of newlines so END_OF_FILE will work
      end loop;
   exit when end_of_file;
      get(x);
      put(x);
   end loop;
end eof;


I personally prefer the following program, which is also correct:


with text_io; use text_io;
procedure eof is
   x: character;
begin
   loop
      begin
         get(x);
         put(x);
      exception
         when end_error => exit;
      end;
   end loop;
end eof;
-- 
Gordon V. Cormack     CS Dept, University of Waterloo, Canada N2L 3G1
gvcormack@waterloo.EDU  gvcormack@uwaterloo.CA  gvcormac@water.BITNET