CSE 109 Test 2  Wednesday  13 April 2005
>>>>>>>>>>>>>>>>>>>>>>>>>>SUGGESTED ANSWERS<<<<<<<<<<<<<<<<<<<<<<<<<<<<
1.  Assume that in developing the class Word from class, I have progressed
to the point of having the declaration below.  Continue the development
by providing the declaration and definition (code) for the concatenation
operator, '+'.  The behavior is indicated by the code below the declaration.
class Word
{public:
  Word(char *x="");
  friend ostream & operator<<(ostream &out,const Word & t);
 private:
  static void check(bool b, char *mess);
  char *str;
};

//sample code, output indicated after second line
  Word a("Hello"),b(" there");
  cout<<(a+b+".")<<(" I see you"+b)<<endl; //Hello there. I see you there
>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
friend Word operator+(const Word &a, const Word &b);

Word operator+(const Word &a, const Word &b)
{char *temp;
 temp=new char[strlen(a.str)+strlen(b.str)+1];
 check(temp!=NULL,"(+) Heap overflow");
 strcpy(temp,a.str);
 strcat(temp,b.str);
 Word t(temp);
 delete[]temp;
 return t;
}
<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
2.  Assume class Lex from program p4.  Write a program that reads one line
of text from the file "ff" and determines whether the syntax of the line
has a sequence of identifiers and (unsigned) numbers such that the sequence
starts and ends with a number or identifier, and between each number or
identifier is exactly one of the symbols, +, -, *, or /.  For example, the
first line below is correct, while the second and third lines are incorrect
(the second because it does not end in a number or identifier, the third
because it has two operators in a row).
6 + 3*4/5-pie
6+3+
6+-5
The output of the program (to the console) should (echo the input and) either
diagnose the error or write the text "Syntactically correct."
>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
#include "lex.h"
void check(bool b, char * mess);
int main()
{int tok;
 ifstream in("ff");
 check(in.good(),"Failure to open file 'ff'");
 Lex lex(in,cout);
 tok=lex.next();
 check(tok==Lex::NUMBER || tok==Lex::IDENT,"Number or ident expected");
 tok=lex.next();
 while(tok!=Lex::ENDOFLINE)
  {check(tok==Lex::SPLUS || tok==Lex::SMINUS
       || tok==Lex::SMUL || tok==Lex::SDIV, "'+', '-', '*', '/' expected");
   tok=lex.next();
   check(tok==Lex::NUMBER || tok==Lex::IDENT,"Number or ident expected");
  }
 cout<<"\nSyntactically correct.\n";
}
void check(bool b, char * mess)
{if(!b)
  {cerr<<"ERROR: "<<mess<<endl;
   exit(1);
  }
}
<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
3. Write a program that determines whether a line of text entered at the
console (keyboard) satisfies the syntax specified by the diagram S in the
following syntax diagrams, where parentheses stand for a circle or oval and
square brackets ([]) stand for boxes.  It should display nothing other than
the syntactical error, if there is one, or a message that the syntax is
acceptable.  Note that blanks (' ') and tabs ('\t') are not acceptable
characters.  Hint: No lexical analyzer is needed, because all symbols are
single characters.  You do not have to worry about blanks and tabs, because
they are illegal.

              +------------------------+
              |    ^             |     |
   S          |    |             |     |
   ----->[A]--+    +-[A]---(-)<--+     +---------->
              |                        |
              +------------------------+
                   ^             |
                   |             |
                   +-[A]<--(+)<--+

   A
   -------------->(a)-------------+
          |                       |
          |                       v
          +-->(*)-->[S]--(/)-[S]--------->
>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>..
#include <stdlib.h>
#include <fstream.h>
class P
 {public:
   P();
   void parse();
  private:
   void S();
   void A();
   static void check(bool b,char *mess);
   char ch;
 };

int main()
 {P p;
  p.parse();
  cout<<"Syntax is correct\n";
 }

P::P(){}

void P::parse()
{cin.get(ch);
 S();
 check(ch=='\n'||ch=='\r',"EOLN expected");
}

void P::S()
{A();
 if(ch=='+')
  while(ch=='+')
    {cin.get(ch);
     A();
    }
 else
  while(ch=='-')
   {cin.get(ch);
    A();
   }
}

void P::A()
{if(ch=='a')
  cin.get(ch);
 else if(ch=='*')
  {cin.get(ch);
   S();
   check(ch=='/',"'/' expected");
   cin.get(ch);
   S();
  }
 else check(false,"'a' or '*' expected");
}

void P::check(bool b,char *mess)
{if(!b)
  {cerr<<"ERROR: "<<mess<<endl;
   exit(1);
  }
}
<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
4. Write MAC3 code that corresponds to the following MCALL program
Hint: Recall the codes HALT(0), READ(1), WRITE(2), ADD(3), SUB(4),
MUL(5), DIV(6), MOV(7), CJMP(8).
    read x
    write 3+2*x
    halt
    end
>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
1110000          1    read x
7990900          2    put 3 at top of stack
7981000          3    push 2
7971100          4    push x
5989897          5    push pop*pop (2*x)
3999998          6    push pop+pop (3+2*x)
2990000          7    write top of stack
0                8    halt
3                9     3
2               10     2
0               11     x
E
<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
