You are on page 1of 199

M. Sc.

Part I [COMPUTER SCIENCE]


Practical Journal [ Principles of Compiler Design ]
Seat Number [ ]

Department of Computer Science and Information Technology


Deccan Education Society’s
Kirti College of Arts, Science and Commerce.
[ NAAC Accredited : “A Grade”]
Department of Computer Science and Information Technology
Deccan Education Society’s
Kirti College of Arts, Science and Commerce.
[ NAAC Accredited : “A Grade”]

CERTIFICATE

This is to certify that Mr./Miss_________________ of M.Sc Part-I [COMPUTER

SCIENCE] with Seat No._______has successfully completed the practical of

Principles of Compiler Design under my supervision in this college during the year

2006 - 2007.

Lecturer-in-charge Head of Department


( Mrs.Akshata Nayak) Dept of Com.Sc and I.T
(Dr. Seema Purohit)
NAAC Accreditation “A” Grade
Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07
Compiler Construction ( Section-I )
INDEX

No. Title Page No. Date Sign

1 Parsing using DFA

2 NFA to DFA

3 Removal of Empty State( λ / є )

4 Removal of Left Recursion

5 LL(1) Parsing Table

6 Warshall’s Algorithm

7 LR(0) Parsing

8 Right & Left Linear Grammars

9 Minimize the Automata

10 Simple Precedence Matrix (SPM)

11 Parsing using SPM

12 Linearizing a given SPM


Parsing using Simple Precedence
13 Function
14 Operator Precedence Matrix (OPM)
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-I)


PRACTICAL 1

Write a program for acceptance of a string using DFA

Suppose the following transition table

a B
0 1 0
1 1 2
2 0 2

Find the string you are enter is accepted by above DFA or not?
PROGRAM:

#include<iostream.h>
#include<conio.h>
#include<process.h>
#include<string.h>

class p_dfa
{
int n,n1,n2,final[10],fa[10][10];
char ch[10],*str;
public:
void accept();
void dfa(char*);
};

void p_dfa::accept()
{
int i,j;
cout << endl << "No. of states in DFA are:";
cin >> n;
cout << endl << "No. of final states in DFA are:";
cin >> n1;
cout << endl << "Enter state number(s) of final states(s):";
for(i=0;i<n1;i++)
cin >> final[i];

cout << endl << "No. of characters you are using in DFA are:";
cin >> n2;
cout << endl << "Enter those characters one by one:" << endl;
for(i=0;i<n2;i++)
cin >> ch[i];

cout << endl << "Describe your DFA" << endl;


cout << endl << "If char 'A' is output from stayte i to state j";
cout << endl << "then write j at combination of i & 'A'" << endl;

for(i=0;i<n2;i++)
cout << "\t" << ch[i];
cout << endl;

for(i=0;i<n;i++)
{
cout << i << "\t";
for(j=0;j<n2;j++)
cin >> fa[i][j];
}
cout << endl << "Enter the string to be tested:";
cin >> str;
dfa(str);
}

void p_dfa::dfa(char *str)


{
int i,j,len,state=0,flag;
char c;
len = strlen(str);

for(i=0;i<len;i++)
{
c = str[i];
for(j=0;j<n2;j++)
{
if(c == ch[j])
{
if(fa[state][j] != 0)
{
state = fa[state][j];
break;
}
else
{
cout << endl << "Error!!!";
cout << endl << "Invalid string";

exit(0);
}
}
}
}
flag=0;
for(i=0;i<n1;i++)
if(state == final[i])
{
cout << endl << "Valid string";
flag=1;
}

if(flag=0)
cout << endl << "Invalid string (Final state never obtained)!!!";
}
void main()
{
p_dfa d;
clrscr();

d.accept();
getch();
}
OUTPUT:

No. of states in DFA are:3

No. of final states in DFA are:1

Enter state number(s) of final states(s):2

No. of characters you are using in DFA are:2

Enter those characters one by one:


ab

Describe your DFA

If char 'A' is output from stayte i to state j


then write j at combination of i & 'A'
a b
0 1 0
1 1 2
2 0 2

1) Enter the string to be tested: aab


Valid string

2) Enter the string to be tested: abab


Error!!!
Invalid string
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-I)


PRACTICAL 2

You are provided with a NFA with λ moves


a. Write the transition table.
b. Write the procedure to convert the NFA with λ closure to it equivalent
without λ moves.
c. Implement it in C++. Finally output the transition table of the converted
NFA.
Consider the following transition table for (a+b)*abb

e a B
0 {1,7} - -
1 {2,4} - -

2 - 3 -
3 {6} - -

4 - - 5
5 {6} - -
6 {1,7} - -

7 - 8 -
8 - - 9
9 - - 10
10 - - -

Write the program to convert the given NFA into DFA


PROGRAM:

//PROGRAM FOR NFA TO DFA CONVERSION.


#include <stdio.h>
#include <iostream.h>
#include <conio.h>

class DFA;

class NFA
{
protected:
struct TR
{
int no_of_o_s; // Number of output states for input
int output_states[10]; // the output states
}tr[20][5]; // Default 15 are States 5 are Inputs

int no_of_states;
char states[20];
// For Start State q0
int start_state;
// For Set Of Final States F
int no_final_states;
int final_states[10];
// Input Set Of Alphabet
int no_inps;
char inputs[5];

public :
void init1(void);
void E_Closure( int state_no );
void PrintFA(void);
friend void NFA_TO_DFA( NFA *N, DFA *D );
friend int TFind( NFA *N, DFA *D, int current, int array[15], int input );
friend int FindEpsi_T( NFA *N, int array[15], int no, int arrayY[20] );
friend void AddState( NFA *N, DFA *D, int current, int array[15], int no, int input,
int found );
};

void NFA :: init1(void)


{
int i,j,k;
cout<<"The NFA Values \n";
cout<<"No. Of States = ";
cin>>no_of_states;
cout<<"Start State = ";
cin>>start_state;
cout<<"No. Of Final States = ";
cin>>no_final_states;
for(i=0;i<no_final_states;i++)
{
cout<<" "<<i<<" th Final State ";
cin>>final_states[i];
}
cout<<"No. Of Inputs = ";
cin>>no_inps;
for(i=0;i<no_inps;i++)
{
cout<<"Enter "<<i<<" th Input Symbol ";
cin>>inputs[i];
}
cout<<"Enter The Transitions \n";
for(i=0;i<no_of_states;i++)
{
cout<<"For State "<<i<<"\n";
for(j=0;j<no_inps;j++)
{
cout<<"No Of Output States For Input "<<inputs[j]<<"=”;
cin>>tr[i][j].no_of_o_s;
for(k=0;k<tr[i][j].no_of_o_s;k++)
{
cout<<"Enter those states :";
cin>>tr[i][j].output_states[k];
}
}
}
}

class DFA
{
private :
struct TR
{
int output_state; // the output state for input
};

struct DState
{
int no_states;
int states[15];
struct TR trn[10];
}DStates[15];

int nDFAstates;
// F
int no_final_states;
int final_states[10];
// Input Alphabet
int no_inps;
char inputs[5];

public :
int start_state;
DFA(void);
friend void NFA_TO_DFA( NFA *N, DFA *D );
friend int TFind( NFA *N, DFA *D, int current, int array[15], int input );
friend int FindEpsi_T( NFA *N, int array[15], int no, int arrayY[20] );
int CheckPrev( int array[15], int no );
friend void AddState( NFA *N, DFA *D, int current, int array[15], int no, int input,
int found );
int AcceptString( int CurrState, char *str, int Pos );
void PrintDFA(void);
};

int closure[15], cl=0;

void main()
{
NFA Nfa;
DFA Dfa;
int i;
char InpStr[10];
clrscr();
Nfa.init1();
Nfa.PrintFA();
NFA_TO_DFA( &Nfa, &Dfa );
Dfa.PrintDFA( );

/* cout << "\nEnter Input String : ";


cin >> InpStr;
if( Dfa.AcceptString( Dfa.start_state, InpStr, 0 ) )
cout <<"\n"<<InpStr<<" String is Accepted by DFA ";
else
cout <<"\n"<<" String is Not Accepted by DFA ";*/
getch();
}

DFA :: DFA(void)
{
int i, j;
for( i = 0; i < 15; i++ )
for( j = 0; j < 10; j++ )
DStates[i].trn[j].output_state = -1;
}

void NFA :: PrintFA(void)


{
int i, j, k;
clrscr();
cout << "\n\n Transition Table For Given NFA\n";
cout << "******************************************************\n";
cout << " STATES INPUTS\n ";
for( i = 0; i < no_inps; i++ )
cout << inputs[i] << "\t\t";
cout << "\n______________________________________________________\n";

for( i = 0; i < no_of_states; i++ )


{
cout << "q" << i ;
for( j = 0; j < no_inps; j++ )
{
cout << "\t\t ";
for( k = 0; k < tr[i][j].no_of_o_s; k++ )
cout << "q" << tr[i][j].output_states[k] << " ";
}
cout << "\n";
}
getch();
}

void NFA :: E_Closure( int state_no )


{
int stack[15], top=0, pop_state, i, j, findflg = 0;

cl = 0;
stack[top] = state_no;
closure[cl++] = state_no;

while( top != -1 )
{
pop_state = stack[top];
top--;

for(i=0; i < tr[pop_state][0].no_of_o_s; ++i)


{
findflg = 0;
for( j = 0; j < cl; j++ )
{
if( tr[pop_state][0].output_states[i] == closure[j] )
findflg = 1;
}
if( !findflg )
{
top++;
stack[top] = tr[pop_state][0].output_states[i];
closure[cl++] = tr[pop_state][0].output_states[i];
}
}
}
}

void NFA_TO_DFA( NFA *N, DFA *D )


{
int i, j, k, l, current, m, found;

int T[15], Y[20];


int nT, nY;

D->start_state = 0;
D->no_final_states = 0;

D->no_inps = N->no_inps;

for( i = 1; i < N->no_inps; i++ )


{
D->inputs[i] = N->inputs[i];
}

current = 0;
cl = 0;

N->E_Closure( N->start_state ); // î-CLOSURE ( q0 ) is in Closure

// Build The First DFA state


current=0;

for( j=0; j< cl; ++j )


D->DStates[current].states[j] = closure[j];

D->DStates[current].no_states = cl;
D->nDFAstates = current;
(D->nDFAstates)++;

while( current < D->nDFAstates )


{
for ( i=1; i < N->no_inps; ++i )
{
nT = TFind( N, D, current, T, i );
nY = FindEpsi_T( N, T, nT, Y );
found = D->CheckPrev( Y, nY );

AddState( N, D, current, Y, nY, i, found );

cout << "Input : " << N->inputs[i] << " => T = { ";
for( l = 0; l < nT; l++ )
cout << T[l] << ", ";

cout << "\b\b } ";


cout << "Y = { ";
for( l = 0; l < nY; l++ )
cout << Y[l] << ", ";
cout << "\b\b } ";
if( !found )
cout << "Not Found\n";
else
cout << "Found\n";
}
current++;
}
}

int TFind( NFA *N, DFA *D, int current, int array[15], int input )
{
int i, j, n, ctr;
ctr = 0;

for( i=0; i<D->DStates[current].no_states; ++i )


{
n = N->tr[ D->DStates[current].states[i] ][input].no_of_o_s;
for( j = 0; j < n; j++ )
{
array[ctr] = N->tr[ D->DStates[current].states[i] ][input].output_states[j];
ctr++;
}
}
return( ctr );
}

int FindEpsi_T( NFA *N, int array[15], int no, int arrayY[20] )
{
int i, j, ctr, dupl, m;
cl = 0;

N->E_Closure( array[0] );

for(j=0; j<cl; ++j)


arrayY[j] = closure[j];

ctr = j; // no of states in arrayY

for(i=1; i<no; ++i)


{
cl=0;
N->E_Closure( array[i] );

for( j=0; j<cl; ++j )


{
dupl = 0;
for(m=0; m<ctr; ++m) // traverse array Y for Duplicate
{
if( closure[j] == arrayY[m] )
dupl = 1;
}
if( !dupl )
arrayY[ctr++] = closure[j];
}
}
return ctr;
}

int DFA :: CheckPrev( int array[30], int no )


{
int i, j, k, l;

for(i=0; i < nDFAstates; ++i)


{
l = 0;
for( j=0; j < DStates[i].no_states; ++j)
{
for( k=0; k<no; ++k )
{
if( DStates[i].states[j] == array[k] )
l++;
}
}
if( DStates[i].no_states == no && l == no )
return( i );
}
return 0;
}

void AddState( NFA *N, DFA *D, int current, int array[15], int no, int input, int found )
{
int i, j, flag;

if( !found )
{
flag = 0;
for(i=0; i < no; ++i)
{
D->DStates[D->nDFAstates].states[i] = array[i];

for(j=0; j < N->no_final_states; ++j)


{
if( D->DStates[D->nDFAstates].states[i] == N->final_states[j] )
{
flag = 1;
break;
}
}
}
if( flag )
{
D->final_states[D->no_final_states] = D->nDFAstates;
D->no_final_states++;
}

D->DStates[D->nDFAstates].no_states = no;
D->DStates[current].trn[input].output_state = D->nDFAstates;
D->nDFAstates++;
}
else
D->DStates[current].trn[input].output_state = found;
}

void DFA :: PrintDFA(void)


{
int i, j, k;
cout << "\n\n Transition Table For Given DFA\n";
cout << "******************************************************\n";
cout << " STATES INPUTS\n";
cout << " ";

for( i = 1; i < no_inps; i++ )


cout << inputs[i] << "\t\t";
cout << "\n------------------------------------------------------\n";

for( i = 0; i < nDFAstates; i++ )


{
cout << "q" << i ;
for( j = 1; j < no_inps; j++ )
{
cout << "\t\t ";
cout << "q" << DStates[i].trn[j].output_state << " ";
}
cout << "\n";
}
cout << "------------------------------------------------------\n";
cout << "Start State is : q" << start_state << "\n";
cout << "Final States : { ";
for( i = 0; i < no_final_states; i++ )
{
cout << "q" << final_states[i] << ", ";
}
cout << "\b\b } ";
getch();
}
OUTPUT:

The NFA Values

No. Of States = 11

Start State = 0

No. Of Final States = 1


0th Final State 10

No. Of Inputs = 3
Enter 0 th Input Symbol e
Enter 1 th Input Symbol a
Enter 2 th Input Symbol b

Enter The Transitions

For State 0
No Of Output States For Input e= 2
Enter those states :1
Enter those states :7
No Of Output States For Input a= 0
No Of Output States For Input b= 0

For State 1
No Of Output States For Input e= 2
Enter those states :2
Enter those states :4
No Of Output States For Input a= 0
No Of Output States For Input b= 0

For State 2
No Of Output States For Input e= 0
No Of Output States For Input a= 1
Enter those states :3
No Of Output States For Input b= 0

For State 3
No Of Output States For Input e= 1
Enter those states :6
No Of Output States For Input a= 0
No Of Output States For Input b= 0

For State 4
No Of Output States For Input e= 0
No Of Output States For Input a= 0
No Of Output States For Input b= 1
Enter those states :5
For State 5
No Of Output States For Input e= 1
Enter those states :6
No Of Output States For Input a= 0
No Of Output States For Input b= 0

For State 6
No Of Output States For Input e= 2
Enter those states :1
Enter those states :7
No Of Output States For Input a= 0
No Of Output States For Input b= 0

For State 7
No Of Output States For Input e= 0
No Of Output States For Input a= 1
Enter those states :8
No Of Output States For Input b= 0

For State 8
No Of Output States For Input e= 0
No Of Output States For Input a= 0
No Of Output States For Input b= 1
Enter those states :9

For State 9
No Of Output States For Input e= 0
No Of Output States For Input a= 0
No Of Output States For Input b= 1
Enter those states :10

For State 10
No Of Output States For Input e= 0
No Of Output States For Input a= 0
No Of Output States For Input b= 0
STATES INPUTS
e a b
______________________________________________________
q0 q1 q7
q1 q2 q4
q2 q3
q3 q6
q4 q5
q5 q6
q6 q1 q7
q7 q8
q8 q9
q9 q10
q10

Input : a => T = { 8, 3 } Y = { 8, 3, 6, 1, 7, 2, 4 } Not Found


Input : b => T = { 5 } Y = { 5, 6, 1, 7, 2, 4 } Not Found
Input : a => T = { 8, 3 } Y = { 8, 3, 6, 1, 7, 2, 4 } Found
Input : b => T = { 9, 5 } Y = { 9, 5, 6, 1, 7, 2, 4 } Not Found
Input : a => T = { 8, 3 } Y = { 8, 3, 6, 1, 7, 2, 4 } Found
Input : b => T = { 5 } Y = { 5, 6, 1, 7, 2, 4 } Found
Input : a => T = { 8, 3 } Y = { 8, 3, 6, 1, 7, 2, 4 } Found
Input : b => T = { 10, 5 } Y = { 10, 5, 6, 1, 7, 2, 4 } Not Found
Input : a => T = { 8, 3 } Y = { 8, 3, 6, 1, 7, 2, 4 } Found
Input : b => T = { 5 } Y = { 5, 6, 1, 7, 2, 4 } Found

Transition Table For Given DFA


******************************************************
STATES INPUTS
a b
------------------------------------------------------
q0 q1 q2
q1 q1 q3
q2 q1 q2
q3 q1 q4
q4 q1 q2
------------------------------------------------------

Start State is : q0

Final States : { q4 }
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-I)


PRACTICAL 3
You are provided with a NFA with λ moves
d. Write the transition table.
e. Write the procedure to find out the λ closure.
f. Implement it in C++. Finally output is the λ closure of particular state.
Consider the following transition table for (a+b)*

E a b
0 {1,7} - -
1 {2,4} - -
2 - 3 -
3 {6} - -
4 - - 5
5 {6} - -
6 {1,7} - -
7 - - -

Write the program to find out the λ closure of given states


PROGRAM:

#include<stdio.h>
#include<conio.h>
#include<process.h>
#include<iostream.h>

class stack
{
public: int top,s[50];
stack(void){top= -1;}
void push(int i);
int pop(void);
void display(void);
int Is_Empty(void);
};

int stack::Is_Empty(void)
{
if(top==-1)
return 1;
else
return 0;
}

void stack::display(void)
{
for(;top>-1;top--)
{
cout<< "\n"<<s[top];
}
getch();
}

int stack::pop(void)
{
if(top==-1)
{
cout<<"\n\n\terror:stack is empty";
getch();
exit(0);
}
return s[top--];
}

void stack::push(int i)
{
if(top==49)
{
cout<<"\n\n\terror::stack is full.....";
getch();
exit(0);
}
s[++top]=i;
}

class NFA
{
public: int TransTable[10][10],Array[100];
char Symbol[10],MarkOn[50];
int NoOfStates,NoOfInputSymbols;
void InputTTable(void);
void PrintTTable(void);
void MarkState(int state);
void UnMarkAll(void);
int Is_Marked(int state);
};

int NFA::Is_Marked(int state)


{
if(MarkOn[state]==0)
return 0;
else
return 1;
}

void NFA::UnMarkAll(void)
{
for(int i=0;i<NoOfStates;i++)
MarkOn[i]=0;
}

void NFA::MarkState(int state)


{
MarkOn[state]=1;
}

void NFA::InputTTable(void)
{
int i,j,pos=0;
clrscr();
cout<<"enter no of states::";
cin>>NoOfStates;
cout<<"enter no of input symbols::";
cin>>NoOfInputSymbols;
cout<<"enter those input symbols::";
for(i=0;i<NoOfInputSymbols;i++)
cin>>Symbol[i];
cout<<"\nEnter the transition table(enter -1 for Halt)";
for(i=0;i<NoOfStates;i++)
for(j=0;j<NoOfInputSymbols;j++)
{
cout<<"\nform state\t "<<i<<"\t on\t"<<Symbol[j]<<"\t:: ";
TransTable[i][j]=pos;
while(1)
{
cin>>Array[pos++];
if(Array[pos-1]==-1)
break;
}
}
}

void NFA::PrintTTable(void)
{
int i,j,pos;
for(i=0;i<NoOfStates;i++)
for(j=0;j<NoOfInputSymbols;j++)
{
cout<<"\n form state"<<i<<"\ton"<<Symbol[j]<<"\t::";
pos=TransTable[i][j];
while(Array[pos]!=-1)
{
cout<<Array[pos++]<<" ";
}
}
}

class state
{
public: int j,Label,E_Closure_Set[50],count;
state(void){count=0;}
void Add_To_E_Closure(int state);
void Calculate_E_Closure(int state,NFA n);
void Disp_E_Closure(int state);
};

void state::Add_To_E_Closure(int stat)


{
E_Closure_Set[count++]=stat;
}

void state::Disp_E_Closure(int state)


{
cout<<endl;
for(int i=0;i<count;i++)
cout<<E_Closure_Set[i]<<" ";
getch();
j=0;
}
void state::Calculate_E_Closure(int stat,NFA n)
{
int pos;
int temp;
stack s;
count=0;
n.UnMarkAll();
clrscr();
s.push(stat);
n.MarkState(stat);
cout<<endl<<endl<<"the epslone closure of"<<stat<<"is::\n\t";
while(!s.Is_Empty())
{
temp=s.pop();
Add_To_E_Closure(temp);
pos=n.TransTable[temp][0];
while(n.Array[pos]!=-1)
{
if(!n.Is_Marked(n.Array[pos]))
{
s.push(n.Array[pos]);
n.MarkState(n.Array[pos]);
}
pos++;
}
}
Disp_E_Closure(stat);
}

int main(void)
{
state state1;
NFA n;
n.InputTTable();
n.PrintTTable();
while(1)
{
cout<<"\n enter the satte for e.closure(-1 for exit)::";
cin>>state1.Label;
if(state1.Label==-1)break;
state1.Calculate_E_Closure(state1.Label,n);
}
return 0;
}
OUTPUT:
enter no of states::8
enter no of input symbols::3
enter those input symbols::e a b

Enter the transition table(enter -1 for Halt)

form state 0 on e :: 1 7 -1

form state 0 on a :: -1

form state 0 on b :: -1

form state 1 on e :: 2 4 -1

form state 1 on a :: -1

form state 1 on b :: -1

form state 2 on e :: -1

form state 2 on a :: 3 -1

form state 2 on b :: -1

form state 3 on e :: 6 -1

form state 3 on a :: -1

form state 3 on b :: -1

form state 4 on e :: -1

form state 4 on a :: -1

form state 4 on b :: 5 -1

form state 5 on e :: 6 -1

form state 5 on a :: -1

form state 5 on b :: -1

form state 6 on e :: 1 7 -1

form state 6 on a :: -1

form state 6 on b :: -1
form state 7 on e :: -1
form state 7 on a :: -1

form state 7 on b :: -1

form state 0 on e ::1 7


form state 0 on a ::-1
form state 0 on b ::-1
form state 1 on e ::2 4
form state 1 on a ::-1
form state 1 on b ::-1
form state 2 on e ::-1
form state 2 on a ::3 -1
form state 2 on b ::-1
form state 3 on e ::6
form state 3 on a ::-1
form state 3 on b ::-1
form state 4 on e ::-1
form state 4 on a ::-1
form state 4 on b ::5
form state 5 on e ::6
form state 5 on a ::-1
form state 5 on b ::-1
form state 6 on e ::1 7
form state 6 on a ::-1
form state 6 on b ::-1
form state 7 on e ::-1
form state 7 on a ::-1
form state 7 on b ::-1

enter the satte for e.closure(-1 for exit)::0


07142

enter the satte for e.closure(-1 for exit)::1


142

enter the satte for e.closure(-1 for exit)::2


2

enter the satte for e.closure(-1 for exit)::3


367142

enter the satte for e.closure(-1 for exit)::4


4

enter the satte for e.closure(-1 for exit)::5


567142

enter the satte for e.closure(-1 for exit)::6


67142

enter the satte for e.closure(-1 for exit)::7


7
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-I)


PRACTICAL 4

You are provided with a grammer


Write an algorithm to remove the left recursion
Implement it in C++.
Consider the Grammer
E -> E + T
E -> T
T -> T * F
T -> F
F -> ( E )
F -> id
Remove the left recursion for above grammer
PROGRAM:

#include<iostream.h>
#include<process.h>
#include<string.h>
#include<conio.h>

class lf
{
int prod,p_new,prd,pflag[10];
char PROD[10][15],
P_NEW[15][15];
public:
void initial();
void input();
void Left_recursion();
void display();
};

void lf::initial()
{
int i,j;
for(i=0;i<15;i++)
{
for(j=0;j<15;j++)
{
PROD[i][j]='\0';
P_NEW[i][j]='\0';
}
}
for(i=0;i<10;i++)
pflag[i]=0;
prod=0;
p_new=0;
}

void lf::input()
{
int i,j;
cout<<endl<<"Enter no.of production are:";
cin>>prod;
cout<<endl<<"enter production:";
for(i=0;i<prod;i++)
cin>>PROD[i];
}

void lf::Left_recursion()
{
char extra[]={'U','V','W','X','Y','Z'};
int i,j,l,x,k,u;
clrscr();
p_new=0;
x=0;
for(i=0;i<prod;i++)
{
if(pflag[i]==0)
{
if(PROD[i][0]==PROD[i][3])
{
pflag[i]=1;
for(j=i+1;j<prod;j++)
{
if((PROD[j][0]==PROD[i][0]) && (PROD[j][0]!=PROD[j][3]))
{
pflag[j]=1;
P_NEW[p_new][0]=PROD[j][0];
P_NEW[p_new][1]='-';
P_NEW[p_new][2]='>';
l=3;
while(PROD[j][l]!='\0')
{
P_NEW[p_new][l]=PROD[j][l];
l++;
}
P_NEW[p_new][l]=extra[x];
p_new++;
P_NEW[p_new][0]=extra[x];
P_NEW[p_new][1]='-';
P_NEW[p_new][2]='>';
u=4;
while(PROD[i][u]!='\0')
{
P_NEW[p_new][u-1]=PROD[i][u];
u++;
}
u--;
P_NEW[p_new][u]=extra[x];
p_new++;
P_NEW[p_new][0]=extra[x];
P_NEW[p_new][1]='-';
P_NEW[p_new][2]='>';
P_NEW[p_new][3]='#';
p_new++;
x++;
}
};
}
else
{
strcpy(P_NEW[p_new],PROD[i]);
p_new++;
}
}
}
}

void lf::display()
{
int i;
cout<<endl<<"production sfter left recursion are:";
for(i=0;i<p_new;i++)
cout<<endl<<P_NEW[i];
}

void main()
{
lf l;
clrscr();
l.initial();
l.input();
l.Left_recursion();
l.display();
getch();
}
OUTPUT:

Enter no.of production are:6

enter production:
E->E+T
E->T
T->T*F
T->F
F->(E)
F->id

production sfter left recursion are:


E->TU
U->+TU
U->#
T->FV
V->*FV
V->#
F->(E)
F->id
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-I)


PRACTICAL 5

Input a grammar from the user. Identify the input Terminals, and Non-terminal
a) Write a C++ Code to compute the FIRST, FOLLOW of all terminal.
b) Write a C++ Code to Compute the LL(1) Parsing Table for the given
grammer.

Consider the grammer,

E -> T E’
E’ -> + T E’
T -> F T’
T’ -> * F T’
F -> ( E )
F -> id
E’ -> ε
T’ -> ε
Compute the FIRST, FOLLOW & build the parsing table.
PROGRAM:

#include<stdio.h>
#include<iostream.h>
#include<conio.h>
#include<ctype.h>
#include<string.h>

class GRAMMER
{

int no_nt;
char NT[20][10];

int no_t;
char T[20][10];

int no_prod;
struct PRD
{
char lhs[10];
char rhs[80];
}PROD[10];

char StartSymbol[10];

struct First_and_Follow
{
char Nt[10];
char Terminals[10][10];
int no_T;
}FIRST[20], FOLLOW[20];

char *First;

public :
char InputString[20];
GRAMMER( void );
void PrintGrammer( void );
int FindFirstSymbol( struct PRD P, char FS[10] );
int IsT_NT( char Symb[10] );
void FindFirstFollow();
char *FindFirst( char Nt[10] );
char *FindFollow( char Nt[10] );
};

int strcmpstr( char *str1, char *str2 );

GRAMMER :: GRAMMER(void)
{
clrscr();

no_nt = 5;
strcpy( NT[0], "E");
strcpy( NT[1], "T");
strcpy( NT[2], "F");
strcpy( NT[3], "E'");
strcpy( NT[4], "T'");

no_t = 6;
strcpy( T[0] ,"+");
strcpy( T[1] , "*");
strcpy( T[2] , "(");
strcpy( T[3] , ")");
strcpy( T[4] , "id");
strcpy( T[5] , "î");

no_prod = 8;
strcpy( PROD[0].lhs , "E");
strcpy( PROD[0].rhs , "T E'");

strcpy( PROD[1].lhs , "E'");


strcpy( PROD[1].rhs , "+ T E'");

strcpy( PROD[2].lhs , "T");


strcpy( PROD[2].rhs , "F T'");

strcpy( PROD[3].lhs , "T'");


strcpy( PROD[3].rhs , "* F T'");

strcpy( PROD[4].lhs , "F");


strcpy( PROD[4].rhs , "( E )");

strcpy( PROD[5].lhs , "F");


strcpy( PROD[5].rhs , "id");

strcpy( PROD[6].lhs , "E'");


strcpy( PROD[6].rhs , "î");

strcpy( PROD[7].lhs , "T'");


strcpy( PROD[7].rhs , "î");

strcpy( StartSymbol , "E");


}

void GRAMMER :: PrintGrammer ( void )


{
cout<<"\nSTART STATE : "<<StartSymbol;

cout<<"\nNon Terminlas : ";


for(int i=0; i<no_nt; ++i )
cout<<"\nNT"<<i+1<<" "<<NT[i];

cout<<"\nTerminals : ";

for(i=0; i<no_t; ++i )


cout<<"\nT"<<i+1<<" : "<< T[i];

cout << "\nProductions : ";

for(i=0;i<no_prod;++i)
{
cout<<"\nProduction No "<<i+1<<" "<<PROD[i].lhs<<"->" ;
cout<<PROD[i].rhs;
}

getch();
}

void GRAMMER :: FindFirstFollow()


{
int i, j, k, l, index,m;
char *trial,*tempLhs,tempRhs;
int res;

strcpy( T[no_t++], "$" );

index = 0;
for( index = 0; index < no_nt; index++ )
{
strset( FIRST[index].Nt, '\0');
for( i = 0; i < no_t; i++ )
strset( FIRST[index].Terminals[i], '\0');
FIRST[index].no_T = 0;
}

for( i = 0; i < no_nt; i++ )


{
strcpy( FIRST[i].Nt, NT[i] );
First = FindFirst( NT[i] );
k = 0;
for( j = 0; First[j] != '\0'; j++ )
{
if( First[j] != ' ' )
{
FIRST[i].Terminals[FIRST[i].no_T][k++] = First[j];
}
else
{
FIRST[i].Terminals[FIRST[i].no_T][k] = '\0';
if( IsT_NT( FIRST[i].Terminals[ FIRST[i].no_T ] ) == 1 )
FIRST[i].no_T++;

k = 0;
}
}
}

index = 0;
for( index = 0; index < no_nt; index++ )
{
strset( FOLLOW[index].Nt, '\0');
for( i = 0; i < no_t; i++ )
strset( FOLLOW[index].Terminals[i], '\0');
FOLLOW[index].no_T = 0;
}

for( i = 0; i < no_nt; i++ )


{
First = FindFollow( NT[i] );
strcpy(trial,First);
strcpy( FOLLOW[i].Nt, NT[i] );
k = 0;
for( j = 0; trial[j] != '\0'; j++ )
{
if( trial[j] != ' ' )
{
FOLLOW[i].Terminals[ FOLLOW[i].no_T ][k++] = trial[j];
}
else
{
FOLLOW[i].Terminals[ FOLLOW[i].no_T ][k] = '\0';
if(IsT_NT( FOLLOW[i].Terminals[ FOLLOW[i].no_T ] ) == 1
)
FOLLOW[i].no_T++;
k = 0;
}
}
}
cout<<"\n\t\t\tFirst of all Non Terminal"<<endl;
for(k =0;k < no_nt;k++)
{
cout << "\nFIRST( " << FIRST[k].Nt << " ) = { ";

for( l = 0; l < FIRST[k].no_T; l++ )


{
cout << FIRST[k].Terminals[l] << ", ";
}
cout << "\b\b }"<<endl;
}
cout<<"\n\t\t\tFollow of all Non Terminal"<<endl;
for( k = 0; k < no_nt; k++ )
{
cout << "\nFOLLOW( " << FOLLOW[k].Nt << " ) = { ";

for( l = 0; l < FOLLOW[k].no_T; l++ )


{
cout << FOLLOW[k].Terminals[l] << ", ";
}
cout << "\b\b }"<<endl;
}
cout<<endl;
for(i=0;i<no_t; i++)
if(strcmp(T[i],"î")!=0)
cout << "\t" << T[i];

for(i=0;i<no_nt;i++)
{
cout << endl;
cout << NT[i];

for(j=0;j<no_t; j++)
{
if(strcmp(T[j],"î")!=0)
{
cout << "\t";
for(k=0;k<FIRST[i].no_T;k++)
{
if(strcmp(FIRST[i].Terminals[k],T[j])==0)
{
for(l=0;l<no_prod;l++)
{
if(strcmp(PROD[l].lhs,NT[i]) == 0)
{
cout << l+1;
goto direct;
}
}
}

if(strcmp(FIRST[i].Terminals[k],"î")==0)
{
for(l=0;l<FOLLOW[i].no_T;l++)
{
res
=strcmp(FOLLOW[i].Terminals[l],T[j]);
if(res==0)
{
for(m=0;m<no_prod;m++)
{

strcpy(tempLhs,PROD[m].lhs);
tempRhs
=PROD[m].rhs[0];

if(strcmp(NT[i],tempLhs)==0 &&
tempRhs=='î')
cout << m+1;
}
goto direct;
}
}
}
}
}
direct:
}
}
}

int GRAMMER :: FindFirstSymbol( struct PRD P, char FS[10] )


{
int k;

for( k=0; P.rhs[k] != '\0'; k++ ) // to find first Symbol in the rhs
{
if( P.rhs[k] != ' ' )
FS[k] = P.rhs[k];
else
break;
}

FS[k] = '\0';

for( k = 0; k < no_t; k++ )


{
if( strcmp( FS, T[k] ) == 0 )
return( 1 );
}

for( k = 0; k < no_nt; k++ )


{
if( strcmp( FS, NT[k] ) == 0 )
return( 2 );
}

return( 0 );
}
int GRAMMER :: IsT_NT( char Symb[10] )
{
int k;

for( k = 0; k < no_t; k++ )


{
if( strcmp( Symb, T[k] ) == 0 )
return( 1 );
}

for( k = 0; k < no_nt; k++ )


{
if( strcmp( Symb, NT[k] ) == 0 )
return( 2 );
}

return( 0 );
}

char * GRAMMER :: FindFirst( char Nt[10] )


{
int i, j, k, l, isTorNT, ProdLoc[10], prods;
char FirstSymbol[10], T_in_First[10] = "";

prods = 0;
for( i = 0; i < no_prod; i++ )
{
if( strcmp( PROD[i].lhs, Nt ) == 0 )
{
ProdLoc[prods++] = i;
}
}

for( i = 0; i < prods; i++ )


{
isTorNT = FindFirstSymbol( PROD[ ProdLoc[i] ], FirstSymbol );

if( isTorNT == 1 ) // if First Symbol is Terminal


{
strcat( T_in_First, FirstSymbol );
strcat( T_in_First, " " );
}
else
{
if( isTorNT == 2 ) // if First Symbol is Non Terminal
{
strcat( T_in_First, FindFirst( FirstSymbol ) );
strcat( T_in_First, " " );
}
}
}

return( T_in_First );
}

char * GRAMMER :: FindFollow( char Nt[10] )


{
int i, j, k, l, m, isTorNT, FindPos, prods, found;
char FirstSymbol[10], T_in_Follow[10] = "";

struct Prod
{
int ProdLoc;
char Symbol[10];
}Prods[10];

found = 0;

for( j = 0; j < no_nt; j++ )


{
if( strcmp( FOLLOW[j].Nt, Nt ) == 0 )
{
found = 1;
break;
}
}

if( found )
{
for( l = 0; l < FOLLOW[j].no_T; l++ )
{
strcat( T_in_Follow, FOLLOW[j].Terminals[l] );
strcat( T_in_Follow, " " );
}
return( T_in_Follow );
}

if( strcmp( Nt, StartSymbol ) == 0 )


strcat( T_in_Follow, "$ " );

prods = 0;
for( i = 0; i < no_prod; i++ )
{
//it returns last char's position of Nt

FindPos = strcmpstr( PROD[i].rhs, Nt );

if( FindPos != -1 )
{
if( strlen( PROD[i].rhs ) == FindPos )
{
if( strcmp( PROD[i].lhs, Nt ) != 0 )
{
strcpy( Prods[prods].Symbol, "á" );
Prods[prods++].ProdLoc = i;
}
}
else
{
j = FindPos;
while( PROD[i].rhs[j] == ' ' )

j++;
k = 0;
while( PROD[i].rhs[j] != '\0' )
{
if( PROD[i].rhs[j] == ' ' )
break;
else
Prods[prods].Symbol[k++] = PROD[i].rhs[j++];
}
Prods[prods].Symbol[k] = '\0';
if( strcmp( PROD[i].lhs, Prods[prods].Symbol ) != 0 )
Prods[prods++].ProdLoc = i;
}
}
}

for( i = 0; i < prods; i++ )


{
if( IsT_NT( Prods[i].Symbol ) == 1 )
{
strcat( T_in_Follow, Prods[i].Symbol );
strcat( T_in_Follow, " " );
}
else
{
if( IsT_NT( Prods[i].Symbol ) == 2 )
{
for( j = 0; j < no_nt; j++ )
{
if( strcmp( FIRST[j].Nt, Prods[i].Symbol ) == 0 )
break;
}

for( l = 0; l < FIRST[j].no_T; l++ )


{
if( strcmp( FIRST[j].Terminals[l], "î" ) == 0 )
{
strcat( T_in_Follow, FindFollow( PROD[ Prods[i].ProdLoc ].lhs )
);
strcat( T_in_Follow, " " );
}
else
{
FindPos = strcmpstr( T_in_Follow, FIRST[j].Terminals[l] );
if( FindPos == -1 )
{
strcat( T_in_Follow,
FIRST[j].Terminals[l] );
strcat( T_in_Follow, " " );
}
}
}
}// if
else
{
if( strcmp( Prods[i].Symbol, "á" ) == 0 )
{
strcat( T_in_Follow,
FindFollow( PROD[ Prods[i].ProdLoc ].lhs ) );
strcat( T_in_Follow, " " );
}
}
}//else
}//for

return( T_in_Follow );
}

int strcmpstr( char *str1, char *str2 )


{
int i, j, pos;

pos = -1;
if( strlen(str1) > strlen(str2) )
{
for( i = 0, j = 0; str1[i] != '\0'; i++ )
{
if( str1[i] == str2[j] )
{
j++;

if( j == strlen( str2 ) && i < strlen( str1 ) && str1[i+1] == ' ' )
{
pos = ++i; // Forwarding pointer to end of str2 in str1
break;
}

if( j == strlen( str2 ) && str1[i+1] == '\0' )


{
pos = ++i; // Forwarding pointer to end of str2 in str1
break;
}

if( str1[i+1] != str2[j] || j == strlen( str2 ))


j = 0;
}
}
}

return pos;
}

int main(void)
{
GRAMMER G1;
int result;
G1.PrintGrammer();
G1.FindFirstFollow();
getch();
return 0;
}
OUTPUT:

Non Terminals :
NT1 E
NT2 T
NT3 F
NT4 E'
NT5 T'

Terminals :
T1 : +
T2 : *
T3 : (
T4 : )
T5 : id
T6 : ε

Productions :
Production No 1 E->T E'
Production No 2 E'->+ T E'
Production No 3 T->F T'
Production No 4 T'->* F T'
Production No 5 F->( E )
Production No 6 F->id
Production No 7 E'->ε
Production No 8 T'->ε

First of all Non Terminal

FIRST( E ) = { (, id }
FIRST( T ) = { (, id }
FIRST( F ) = { (, id }
FIRST( E' ) = { +, ε }
FIRST( T' ) = { *, ε }

Follow of all Non Terminal

FOLLOW( E ) = { $, ) }
FOLLOW( T ) = { +, $, ) }
FOLLOW( F ) = { *, +, $, ) }
FOLLOW( E' ) = { $, ) }
FOLLOW( T' ) = { +, $, ) }

+ * ( ) id $
E 1 1
T 3 3
F 5 5
E' 2 7 7
T' 8 4 8 8
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-I)


PRACTICAL 6

Warshall’s Algorithm

You are given Warshall’s algorithm. Write a C-program to accept the following
initial matrix.

000010
000100
000010
010000
100000
010000

Perform the steps of Warshall’s Algorithm and output the final matrix

OUTPUT is :
100010
010100
100010
010100
100010
010100
Program:

#include <iostream.h>
#include <conio.h>
#include <string.h>

void print(int m[6][6]);

void main()
{
int i,j,k;
int m[6][6]={
0,0,0,0,1,0,
0,0,0,1,0,0,
0,0,0,0,1,0,
0,1,0,0,0,0,
1,0,0,0,0,0,
0,1,0,0,0,0
};
clrscr();
cout<<"\n\n\t\tInitial Matrix\n\n";

print(m);
getch();

for(k=0;k<6;++k)
{
for(i=0;i<6;++i)
{
for(j=0;j<6;++j)
{
if(m[i][k]==m[k][j] && 1 ==m[k][j])
{
m[i][j]=1;
}
}
}
}

cout<<"\n\n\nMatrix after applying WARSHALL'S


Algorithm\n\n";
print(m);
getch();
}

void print(int m[6][6])


{
int i,j;
cout<<(char)218<<"\t\t\t\t\t\t"<<(char)191<<"\n";
cout<<(char)179<<"\t\t\t\t\t\t"<<(char)179<<"\n";
for(i=0;i<6;++i)
{
cout<< (char)179<<"\t\t\t\t\t\t"<< (char)179<<"\n";
for(j=0;j<6;++j)
{
cout<<m[i][j]<<"\t";

}
}
cout<<(char)179<<"\n";
cout<<(char)192<<"\t\t\t\t\t\t"<<(char)217<<"\n";

OUTPUT:

Initial Matrix

0 0 0 0 1 0
0 0 0 1 0 0
0 0 0 0 1 0
0 1 0 0 0 0
1 0 0 0 0 0
0 1 0 0 0 0

Matrix after applying WARSHALL'S Algorithm

1 0 0 0 1 0
0 1 0 1 0 0
1 0 0 0 1 0
0 1 0 1 0 0
1 0 0 0 1 0
0 1 0 1 0 0
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-I)


PRACTICAL 7

Input a CFG
1) Write a program to compute the SLR(0) items for the grammar.
2) Write a program to print the parsing table for the given grammar.
PROGRAM:

//PROGRAM FOR SLR PARSER .

#include<stdio.h>
#include<conio.h>
#include<string.h>
#include<ctype.h>

unsigned char prod[10][10]=


{"A->E",
"E->E+T",
"E->T",
"T->T*F",
"T->F",
"F->(E)",
"F->i"
};

int tp = 7,S = 0,tt = 5,tnt = 3;


int i=0,j=0,State[20];

const unsigned char NT[10]={"ETF"},T[10]={"+*()i$"},


TNT[15]={"ETF+*()i"};
char foll[5][10]={"+)$","+*)$","+*)$"};

struct node
{
int pno,dpos;
};

struct t
{
char s;
int n;
};

struct t1
{
struct t lr[10];
int group[5];
};

struct t1 action[15];
struct node closure[12][12];
int g[15][10];

void main()
{
int clno,no=0,x,y,k,l,z,len,count=-1,d=0;
void Find_Closure(int,int);
void Sort_Closure(int,int);
int Added(int);
int Find_T_index(char);
int Find_NT_index(char);
void Print_Tab(int);
void display_group(void);
closure[i][j].pno=0;
closure[i][j++].dpos=3;
Find_Closure(no,3);
Sort_Closure(i,j);
State[i]=j;
S=1;
do
{
count++;
z=State[count];
for(k=0;k<tnt+tt;k++)
{
i++;
j=0;
d=0;
for(l=0;l<z;l++)
{
x=closure[count][l].pno;
y=closure[count][l].dpos;
if(prod[x][y]==TNT[k])
{
d=1;
closure[i][j].pno=x;
closure[i][j++].dpos=++y;
if((y<strlen(prod[x]))&&(isupper(prod[x][y])))
Find_Closure(x,y);
}
}
if(d==0)
{
i--;
continue;
}

Sort_Closure(i,j);
State[i]=j;
clno=Added(i-1);
if(clno==-1)
clno=i;
if(isupper(TNT[k]))
action[count].group[k]=clno;
else
{
action[count].lr[k-tnt].s='S';
action[count].lr[k-tnt].n=clno;
}
if(Added(i-1) != -1)
i--;
else
{
S++;
for(l=0;l<State[l];l++)
{
if(closure[i][l].pno==0)
{
action[i].lr[tt].s='A';
continue;
}
len=strlen(prod[closure[i][l].pno]);
if(len==closure[i][l].dpos)
{
char v = prod[closure[i][l].pno][0];
int u = Find_NT_index(v);
for(x=0;x<strlen(foll[u]);x++)
{
int w=Find_T_index(foll[u][x]);
action[i].lr[w].s='R';
action[i].lr[w].n=closure[i][l].pno;
}
}
}
}
}
}while(count != S);
Print_Tab(S);
getch();
display_group();
getch();
}

void Print_Tab(int states)


{
int i,j,lin=3;
clrscr();
printf("\t\t");
for(i=0;i<=tt;i++)
printf("%c\t",T[i]);
for(i=0;i<tnt;i++)
printf("%c\t",NT[i]);
for(i=0;i<=states;i++)
{
gotoxy(1,lin);
printf("I%d\t",i);
for(j=0;j<=tt;j++)
{
if(action[i].lr[j].s !='\x0')
{
printf("%c",action[i].lr[j].s);
if(action[i].lr[j].s=='A')
continue;
printf("%d",action[i].lr[j].n);
printf("\t");
}
else
printf("\t");
}
for(j=0;j<tnt;j++)
{
if(action[i].group[j])
{
printf(" %2d",action[i].group[j]);
printf("\t");
}
else
printf("\t");
}
lin++;
}
return;
}

void Sort_Closure(int clno,int prodno)


{
int i,j;
struct node temp;
for(i=0;i<prodno-1;i++)
{
for(j=i+1;j<prodno;j++)
{
if(closure[clno][i].pno > closure[clno][j].pno)
{
temp=closure[clno][i];
closure[clno][i]=closure[clno][j];
closure[clno][j]=temp;
}
}
}
for(i=0;i<prodno-1;i++)
{
for(j=i+1;j<prodno;j++)
{
if((closure[clno][i].dpos>closure[clno][j].dpos)
&& (closure[clno][i].pno==closure[clno][j].pno))
{
temp=closure[clno][i];
closure[clno][i]=closure[clno][j];
closure[clno][j]=temp;
}
}
}
}

int Added(int n)
{
int j,k,d=1;
for(k=0;k<=n;k++)
{
if(State[k]==State[n+1])
{
d=0;
for(j=0;j<State[k];j++)
{
if((closure[k][j].pno != closure[n+1][j].pno)
|| (closure[k][j].dpos != closure[n+1][j].dpos))
break;
else
d++;
}
if(d==State[k])
return(k);
}
}
return(-1);
}

void Find_Closure(int no,int dp)


{
int k;
char temp[5];
if(isupper(prod[no][dp]))
{
for(k=0;k<tp;k++)
{
if(prod[k][0]==prod[no][dp])
{
closure[i][j].pno=k;
closure[i][j++].dpos=3;
if((isupper(prod[k][3])) &&(prod[k][3] !=
prod[k][0]))
Find_Closure(k,3);
}
}
}
return;
}
int Find_NT_index(char c)
{
int i;
for(i=0;i<tnt;i++)
if(NT[i]==c)
return(i);
return(-1);
}

int Find_T_index(char c)
{
int i;
for(i=0;i<tt;i++)
if(T[i]==c)
return(i);
return(-1);
}

void display_group()
{
int i,j,k,dot_print=0;

for(i=0;i<S;++i)
{
printf("\nI%d:",i);
for(j=0;j<State[i];++j)
{

printf("\n\t%c->",prod[closure[i][j].pno][0]);
dot_print=0;
for(k=3;k<strlen(prod[closure[i][j].pno]);++k)
{
if(k==closure[i][j].dpos)
{
printf(".%c",prod[closure[i][j].pno][k]);
dot_print=1;

}
else
printf("%c",prod[closure[i][j].pno][k]);
}
if(dot_print!=1)
{
printf(".",prod[closure[i][j].pno][k]);
}
}
}
}
OUTPUT:

+ * ( ) i $
E T F
-------------------------------------------------------------
I0 S4 S5 1 2
3
-------------------------------------------------------------
I1 S6 A
-------------------------------------------------------------
I2 R2 S7 R2
-------------------------------------------------------------
I3 R4 R4 R4 A
-------------------------------------------------------------
I4 S4 S5 8 2 3
-------------------------------------------------------------
I5 R6 R6 R6 A
-------------------------------------------------------------
I6 S4 S5 9 3
-------------------------------------------------------------
I7 S4 S5 10
-------------------------------------------------------------
I8 S6 S11
-------------------------------------------------------------
I9 R1 S7 R1
-------------------------------------------------------------
I10 R3 R3 R3
-------------------------------------------------------------
I11 R5 R5 R5
-------------------------------------------------------------
I12 S4 10
-------------------------------------------------------------

I0:
A->.E
E->.E+T
E->.T
T->.T*F
T->.F
F->.(E)
F->.i

I1:
A->E.
E->E.+T

I2:
E->T.
T->T.*F
I3:
T->F.

I4:
E->.E+T
E->.T
T->.T*F
T->.F

I5:
F->i
I6:
E->E+.T
T->.T*F
T->.F
F->.(E)
F->.i
I7:
T->T*.F
F->.(E)
F->.i
I8:
E->E.+T
F->(E.)
I9:
E->E+T.
T->T.*F
I10:
T->T*F.
I11:
F->(E)
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-I)


PRACTICAL 8

You are provided with a Right Linear grammar below. Perform the
following on to it.
a. Define Left Linear & Right Linear Grammar.
b. Write the pseudo-code for converting Right Linear Grammar to
Left Linear Grammars.
c. Write a C program to convert the Right Linear Grammar given
below to Left Linear Convert the given Right Linear grammar to
Left Linear Grammar.
d. Clearly define the new Non-Terminals, Terminals, Productions &
the Start state of the converted grammar.
Input Î
S -> a
S-> bU
S-> bR
R->abaU
R->U
U->b
U->aS
PROGRAM:

#include<iostream.h>
#include<conio.h>
#include<math.h>
#include<string.h>

void main()
{
char right[10][10]={"S->a","S->bU","S->bR","R->abaU","R->U","U->b","U->aS");
char left[10][10]={"","","","","","",""};
clrscr();
char ter[5]={'a','b'};
char nonter[10]={'S','U','R'};
char sym[10]={'e','e','o'};
int i,j,k,l,m;
cout<<"*****************RIGHT Linear Grammar***********"<<endl;
for(i=0;i<=6;i++)
{
cout<<i<<" "<<right[i];
cout<<"\n";
}
cout<<endl;
k=0;
m=0;
for(i=0;i<7;i++)
{
for(j=0;j<strlen(right[i]);i++)
{
k=i;
/* For length equal to 4*/
if(strlen(right[i])==4)
{
for(int n=0;n<strlen(ter);n++)
{
l=0;
if(right[i][3]==ter[n])
{
left[k][l]=sym[m];
l++;
left[k][l]=right[i][j];
l++;
left[k][l]=right[i][j+3];
m=m+1;
}
}
for(int n1=0;n1<strlen(nonter);n++)
{
l=0;
if(right[i][3]==nonter[n1])
{
left[k][l]=right[i][3];
l++;
left[k][l]=right[i][0];
}
}
}
/*Length Greater than 4*/
else
{
l=0;
char temp;
temp=right[i][l];
left[k][l]=right[i][strlen(right[i]-1];
l++;
left[k][l]=temp;
for(int i1=3;i1<(strlen(right[i]-1);i++)
{
l++;
left[k][l]=right[i][i1];
}
}
}
cout<<"*********LEFT Linear Grammar********"<<endl;
for(int o=0;o<7;o++)
{
cout<<o<<""<<left[o][o]<<"->";
for(int o1=1;o1<strlen(left[o]);o1++)
{
cout<<left[o][o1];
}
cout<<"\n";
}
getch();
}
}
OUTPUT:

*********** RIGHT Linear Grammar **********


0 S->a
1 S->bU
2 S->bR
3 R->abaU
4 R->U
5 U->b
6 U->aS

*********** LEFT Linear Grammar *************

0 ->Sa
1 U->Sb
2 R->Sb
3 U->RaRb
4 U->R
5 o->Ub
6 S->Ua
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-I)


PRACTICAL 9
Minimize Automata

Write a c program to track of suitable representation of the productions with


suitable data structure.Input or code the following number of transition
symbols,the number of DFA states and destination states for all transition
symbols on all states.

Input the following transitions


a b

A B C

B B D

C B C

D B E

E B C

and the minimize number of DFA states and print the minimize DFA transition table.

a b

A B A

B B D

D B E

E B A
PROGRAM:

Minimize Automata
Coding:

#include<stdio.h>
#include<conio.h>
#include<math.h>
#include<iostream.h>
#include<string.h>
int state_no(char);
char dfa[5][4]={"ABC",
"BBD",
"CBC",
"DBE",
"EBC"};
void main()
{
int i,j,k,l,m,a,b,c,d,e,f,g,h;
clrscr();
char final_state[5];
final_state[0]='E';
final_state[1]='\0';
char group[4][4];
char new_group[5][4];

cout<<"********* DFA *******"<<endl;


cout<<""<<"\t"<<"a"<<"\t"<<"b"<<endl;
for(i=0;i<5;i++)
{
for(j=0;j<=2;j++)
{
cout<<dfa[i][j];
cout<<"\t";
}
cout<<endl;
}
cout<<"Give Final State="<<" "<<final_state<<endl;

/* This use to find min DFA */


k=0;l=0;
q:
for(i=0;i<=4;i++)
{
for(j=1;j<3;j++)
{
if(dfa[i][j]==final_state[k])
{
k++;
final_state[k]=dfa[i][0];
l++;
goto q;
}
}
}

c=1;d=0;e=0;
for(a=0;a<=4;a++)
{
for(b=0;b<=4;b++)
{
if(b==a)
{
b++;
}
if((dfa[a][c]==dfa[b][c]) && (dfa[a][c+1]==dfa[b][c+1]))
{
group[d][e]=dfa[a][0];
e++;
group[d][e]=dfa[b][0];
d++;

break;
}
}
}

for(int q=0;q<4;q++)
{
for(m=0;m<4;m++)
{
if(final_state[q]<final_state[m])
{
char temp=final_state[q];
final_state[q]=final_state[m];
final_state[m]=temp;
}
}
}
cout<<endl<<endl<<"********** MIN DFA ***********"<<endl;
cout<<" "<<"\ta\tb"<<endl;

for(int o=0;o<=3;o++)
{
int ff=state_no(final_state[o]);
if(dfa[ff][1]==group[0][1])
dfa[ff][1]=group[0][0];
if(dfa[ff][2]==group[0][1])
dfa[ff][2]=group[0][0];
cout<<final_state[o]<<"\t"<<dfa[ff][1]<<"\t"<<dfa[ff][2]<<endl;
}

getch();
}
int state_no(char cc)
{
for(int aa=0;aa<=4;aa++)
{
if(dfa[aa][0]==cc)
{
return(aa);
}
}
return(0);
}

OUTPUT:

********DFA*****
a b
A B C
B B D
C B C
D B E
E B C
Final State=E

************MIN DFA*******
a b
A B A
B B D
D B E
E B A
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-I)

PRACTICAL 10

Simple Precedence Matrix


You have been given the following rules to obtain the ‘Less –Than’ and ‘Greater-Than’
matrices.

Less Than Æ = ( First )+


Greater Than Æ = ( LAST+ )T = ( FIRST* )

Write a C-Program to extract The First, Equal (Plus_Minus) and Last matrices from the

following Grammar. By using the above rules obtain the ‘Less Than’ , ‘Greater Than’

matrices and by superimposition of the three matrices obtain and print the SPM.

Enter the following grammar g : { N,T,P,S }


Productions P : Z ÆbMb
MÆ(L

MÆa
LÆMa)
PROGRAM:
Simple Precedance Matrix

Coding:

#include<stdio.h>
#include<conio.h>
#include<string.h>
//#include"temparr.h"
char prod[][4]={"bMb","(L","Ma)","a"},rhs[4]={'z','M','L','M'};char symbs[15];
int equalto[7][7],first[7][7],last[7][7],lastT[7][7],firstST[7][7],gr[7][7],gr1[7][7],lr[7][7],flag;
int spm[7][7];
void main()
{
clrscr();
int i,j;
int func(char c);
void temparr();
void equaltof();
void firstplusf();
void lastplusf();
void multi(int arr1[7][7],int arr2[7][7],int arr3[7][7]);
temparr();
equaltof();
clrscr();
firstplusf();
clrscr();
lastplusf();
flag=1;
multi(equalto,first,lr);
flag=2;
multi(lastT,equalto,gr);
flag=3;
multi(gr,firstST,gr1);
clrscr();
printf("SPM:-\n\n");
for(i=0;i<=6;i++)
printf("\t%c",symbs[i]);
printf("\n\n");
for(i=0;i<=6;i++)
{
printf("%c\t",symbs[i]);
for(j=0;j<=6;j++)
{ if(equalto[i][j]==1)
spm[i][j]=-1;
if(lr[i][j]==1)
spm[i][j]=1;
if(gr1[i][j]==1)
spm[i][j]=2;
printf("%d\t",spm[i][j]);
}
printf("\n\n");
}
printf("equal precedence:-(-1)\n");
printf("less than precedence:-(1)\n");
printf("greater than precedence:-(2)\n");
getch();
}
int func(char c)
{
int i,j,len;len=strlen(symbs);
for(i=0;i<len;i++)
{
if(c==symbs[i])
{j=i;break;}
}
return j;
}
void equaltof()
{
int i,j,k,a,b,c;
for(i=0;i<=3;i++)
{
j=0;
while(prod[i][j]!='\0')
{
a=func(prod[i][j]);
j++;
if(prod[i][j]!='\0')
{
b=func(prod[i][j]);
}
else
break;
equalto[a][b]=1;
}
}
printf("(+-) MATRIX:-\n");
for(i=0;i<=6;i++)
printf("\t%c",symbs[i]);
printf("\n\n");
for(i=0;i<=6;i++)
{
printf("%c\t",symbs[i]);
for(j=0;j<=6;j++)
printf("%d\t",equalto[i][j]);
printf("\n\n");
}
getch();
}
void firstplusf()
{
int i,j,k,a,b,c;
for(i=0;i<=3;i++)
{
a=func(rhs[i]);
b=func(prod[i][0]);
first[a][b]=1;
firstST[a][b]=1;
}
printf("FIRST+ MATRIX:-\n");
for(i=0;i<=6;i++)
printf("\t%c",symbs[i]);
printf("\n\n");
for(i=0;i<=6;i++)
{
printf("%c\t",symbs[i]);
for(j=0;j<=6;j++)
{
if(first[i][j]==1)
{
for(k=0;k<=6;k++)
if(first[j][k]==1)
{
first[i][k]=1;
firstST[i][k]=1;
}
}
printf("%d\t",first[i][j]);
}
firstST[i][i]=1;
printf("\n\n");
}
getch();clrscr();
printf("FIRST* MATRIX:-\n");
for(i=0;i<=6;i++)
printf("\t%c",symbs[i]);
printf("\n\n");
for(i=0;i<=6;i++)
{
printf("%c\t",symbs[i]);
for(j=0;j<=6;j++)
printf("%d\t",firstST[i][j]);
printf("\n\n");
}
getch();

}
void lastplusf()
{
int i,j,k,a,b,c;char z;
for(i=0;i<=3;i++)
{
a=func(rhs[i]);
c=strlen(prod[i]);
b=func(prod[i][c-1]);
last[a][b]=1;
}
printf("LastT MATRIX:-\n");
for(i=0;i<7;i++)
printf("\t%c",symbs[i]);
printf("\n\n");
for(i=0;i<7;i++)
{
printf("%c\t",symbs[i]);
for(j=0;j<7;j++)
{
if(last[i][j]==1)
{
for(k=0;k<7;k++)
if(last[j][k]==1)
last[i][k]=1;
}
if(last[i][j]==1)lastT[j][i]=1;//transpose of last
printf("%d\t",lastT[i][j]);
}
printf("\n\n");
}
getch();
}
void multi(int arr1[7][7],int arr2[7][7],int gr[7][7])
{
clrscr();
int i,j,k,mul,sum=0;
for(i=0;i<=6;i++)
{
for(j=0;j<=6;j++)
{
sum=0,mul=0;
for(k=0;k<=6;k++)
{
mul=arr1[i][k]*arr2[k][j];
sum=sum+mul;
}
gr[i][j]=sum;
}
}
if(flag==1)printf("Less Than:-\n\n");
if(flag==2)printf("Lastpl_Trans*equalto:-\n\n");
if(flag==3)printf("Greater Than:-\n\n");
for(i=0;i<7;i++)
printf("\t%c",symbs[i]);
printf("\n\n");
for(i=0;i<7;i++)
{
printf("%c\t",symbs[i]);
for(j=0;j<7;j++)
{
printf("%d\t",gr[i][j]);
}
printf("\n\n");
}
getch();
}
void temparr()
{
int i,j,k,l=0,flag=0,len,len1,flag1,len2;
for(i=0;i<4;i++)
{
len=strlen(prod[i]);
if(i==0)
{
symbs[0]=rhs[0];
if(symbs[0]!=prod[0][0])
symbs[++l]=prod[0][0];
k=1;
}
else
{
k=0;len2=strlen(symbs);
for(j=0;j<len2;j++)
{
flag1=0;
if(symbs[j]==rhs[i])
{
flag1=1;break;
}
}
if(flag1!=1)
symbs[++l]=rhs[i];
}
for(;k<len;k++)
{
flag=0;len1=strlen(symbs);
for(j=0;j<len1;j++)
{
if(symbs[j]==prod[i][k])
{
flag=1;break;
}
}
if(flag!=1)
symbs[++l]=prod[i][k];
}
}
}

Output:
Less than matrix is :

Greater than matrix is :

SPM

Z b M L a ( )

Z 0 0 0 0 0 0 0

b 0 0 -1 0 0 1 0

M 0 -1 0 0 0 -1 0

L 0 0 1 1 -1 1 0

a 0 2 0 0 0 2 0

( 0 2 0 0 0 2 -1

) 0 2 0 0 0 2 0

equal precedence:-(-1)
less than precedence:-(-1)
greater than precedence:-(-2)
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-I)

PRACTICAL 11

Parsing using Simple Precedence Matrix ( SPM )


You are given a SPM of order m * m (m =7,8,9,10).Write a C-program to implement the

parsing algorithm for the SPM. Input the following Grammar and parse the strings given

below:

Grammar G:{N,T,P,S}

Productions P:
ZÆbMb
MÆ( L
MÆa
LÆMa)

SPM

Parse the Strings using above SPM :


b ( aa ) b
b ((aa)a)b
b ((aaa)a)b
Output the step by step reduction.
PROGRAM:
// Parsing using SPM
#include<stdio.h>
#include<iostream.h>
#include<conio.h>
#include<ctype.h>
#include<string.h>
#include<stdlib.h>

class SPM
{
int no_symb;
char symb[20];
char spm[20][20];

int no_nt;
char NT[20][10];

int no_t;
char T[20][10];

int no_prod;
struct PRD
{
char lhs[10];
char rhs[20];
}prod[10];

char StartSymbol[10];
char stack[20][20];
char opr[20];
char input[20][20];
char inputString[20];
int parseStep;
int stackMem;

public:
void inputSPM();
void printSPM();
void parseString();
int getSymbPos(char);
void convInput(int);
void convStack(int);
char InputString[20];
void PrintGrammer(void);
void copyInput();
void printParseTable();
};

void SPM :: inputSPM()


{
int i,j;
clrscr();

no_nt = 3;
strcpy( NT[0], "R");
strcpy( NT[1], "S");
strcpy( NT[2], "T");

no_t = 6;
strcpy( T[0] ,"a");
strcpy( T[1] ,"^");
strcpy( T[2] ,",");
strcpy( T[3] ,"(");
strcpy( T[4] ,")");
strcpy( T[5] ,"$");

no_symb=9;
symb[0]='R';
symb[1]='S';
symb[2]='T';
symb[3]='a';
symb[4]='^';
symb[5]=',';
symb[6]='(';
symb[7]=')';
symb[8]='$';

no_prod = 6;

strcpy( prod[0].lhs , "S");


strcpy( prod[0].rhs , "a");

strcpy( prod[1].lhs , "S");


strcpy( prod[1].rhs , "^");

strcpy( prod[2].lhs , "S");


strcpy( prod[2].rhs , "(R)");

strcpy( prod[3].lhs , "T");


strcpy( prod[3].rhs , "S,T");

strcpy( prod[4].lhs , "T");


strcpy( prod[4].rhs , "S");

strcpy( prod[5].lhs , "R");


strcpy( prod[5].rhs , "T");

strcpy( StartSymbol , "S");


strcpy(inputString,"(a,a)");

spm[0][0]='0';
spm[0][1]='0';
spm[0][2]='0';
spm[0][3]='0';
spm[0][4]='0';
spm[0][5]='0';
spm[0][6]='0';
spm[0][7]='=';
spm[0][8]='0';

spm[1][0]='0';
spm[1][1]='0';
spm[1][2]='0';
spm[1][3]='0';
spm[1][4]='0';
spm[1][5]='=';
spm[1][6]='0';
spm[1][7]='>';
spm[1][8]='0';

spm[2][0]='0';
spm[2][1]='0';
spm[2][2]='0';
spm[2][3]='0';
spm[2][4]='0';
spm[2][5]='0';
spm[2][6]='0';
spm[2][7]='>';
spm[2][8]='0';

spm[3][0]='0';
spm[3][1]='0';
spm[3][2]='0';
spm[3][3]='0';
spm[3][4]='0';
spm[3][5]='>';
spm[3][6]='0';
spm[3][7]='>';
spm[3][8]='>';

spm[4][0]='0';
spm[4][1]='0';
spm[4][2]='0';
spm[4][3]='0';
spm[4][4]='0';
spm[4][5]='>';
spm[4][6]='0';
spm[4][7]='>';
spm[4][8]='>';

spm[5][0]='0';
spm[5][1]='<';
spm[5][2]='=';
spm[5][3]='<';
spm[5][4]='<';
spm[5][5]='0';
spm[5][6]='<';
spm[5][7]='0';
spm[5][8]='0';

spm[6][0]='=';
spm[6][1]='<';
spm[6][2]='<';
spm[6][3]='<';
spm[6][4]='<';
spm[6][5]='0';
spm[6][6]='<';
spm[6][7]='0';
spm[6][8]='0';

spm[7][0]='0';
spm[7][1]='0';
spm[7][2]='0';
spm[7][3]='0';
spm[7][4]='0';
spm[7][5]='>';
spm[7][6]='0';
spm[7][7]='>';
spm[7][8]='>';

spm[8][0]='0';
spm[8][1]='0';
spm[8][2]='0';
spm[8][3]='<';
spm[8][4]='<';
spm[8][5]='0';
spm[8][6]='<';
spm[8][7]='0';
spm[8][8]='0';

parseStep=0;
}

void SPM :: printSPM()


{
int i,j;
cout << endl << "\t";
for(i=0;i<no_symb;i++)
cout << symb[i] << "\t";

for(i=0;i<no_symb;i++)
{
cout << endl << symb[i];
for(j=0;j<no_symb;j++)
cout << "\t" << spm[i][j];
}
}

void SPM :: printParseTable()


{
int i;

cout << endl << endl << "Stack\tOpr\tInput";


printf("%d",parseStep);
for(i=0;i<parseStep;i++)
cout << endl << stack[i] << "\t" << opr[i] << "\t" << input[i];
}

void SPM :: PrintGrammer(void)


{
cout<<"\nSTART STATE : "<<StartSymbol;

cout<<"\nNon Terminlas : ";


for(int i=0; i<no_nt; ++i )
cout<<"\nNT"<<i+1<<" "<<NT[i];

cout<<"\nTerminals : ";
for(i=0; i<no_t; ++i )
cout<<"\nT"<<i+1<<" : "<< T[i];

cout << "\nProductions : ";


for(i=0;i<no_prod;++i)
{
cout<<"\nProduction No "<<i+1<<" "<<prod[i].lhs<<"->" ;
cout<<prod[i].rhs;
}

getch();
}

int SPM :: getSymbPos(char symbol)


{
int i;
for(i=0;i<no_symb;i++)
if(symb[i] == symbol)
return i;
}

void SPM :: parseString()


{
char temp,*startSymCheck;

parseStep=0;
strcpy(stack[0],"$");
opr[0]='<';
strcpy(input[0],inputString);
strcat(input[0],"$");
strcpy(startSymCheck,"$");
strcat(startSymCheck,StartSymbol);
stackMem=0;

clrscr();
while(strcmp(input[parseStep],"$") != 0 || strcmp(stack[parseStep],"$") != 0)
{
printf("\n%s\t%s",stack[parseStep],input[parseStep]);
parseStep++;
strcpy(input[parseStep],input[parseStep-1]);
strcpy(stack[parseStep],stack[parseStep-1]);

if(strcmp(stack[parseStep],startSymCheck) == 0 &&
strcmp(input[parseStep],"$") == 0)
break;

if(
spm[getSymbPos(stack[parseStep][stackMem])][getSymbPos(input[parseStep][0])] == '<' ||

spm[getSymbPos(stack[parseStep][stackMem])][getSymbPos(input[parseStep][0])]
== '=')
{
if(
spm[getSymbPos(stack[parseStep][stackMem])][getSymbPos(input[parseStep][0])] == '<')
opr[parseStep]='<';
else
opr[parseStep]='=';

temp = input[parseStep][0];
convInput(parseStep);
stack[parseStep][++stackMem] = temp;
stack[parseStep][stackMem+1] = '\0';
}
else

if(spm[getSymbPos(stack[parseStep][stackMem])][getSymbPos(input[parseStep][0])]
== '>')
{
opr[parseStep]='>';
convStack(parseStep);
}
else
{
cout << "\nError in string";
getch();
exit(0);
}
}
}

void SPM :: copyInput()


{
int i;
for(i=0;i<strlen(inputString);i++)
input[0][i]=inputString[i];
input[0][i]='\0';
}

void SPM :: convInput(int step)


{
int i;
for(i=0;i<strlen(input[step]);i++)
input[step][i]=input[step][i+1];
}

void SPM :: convStack(int step)


{
int i,startPos,j,s,k;
char *substr,*newstr;
char change='y';

for(i=0;i<no_prod;i++)
{
strcpy(newstr,stack[step]);
if((substr=strstr(newstr,prod[i].rhs)) != NULL)
{
startPos=0;
s=0;
k=0;
//newstr[strlen(stack[step])]='\0';
checkAgain:

s=substr-newstr;
startPos=startPos+s+k;
k++;
for(j=s+1;j<strlen(newstr);j++)
newstr[j-s-1] = substr[j-s];
newstr[j-s-1]='\0';
if((substr=strstr(newstr,prod[i].rhs)) != NULL)
goto checkAgain;

if(strlen(stack[step]) == strlen(prod[i].rhs) + startPos)


{
stackMem = stackMem - strlen(prod[i].rhs) + 1;
stack[step][startPos]=prod[i].lhs[0];
for(j = startPos+1 ; j < startPos + strlen(prod[i].rhs) ; j++)
stack[step][j]=stack[step][j+strlen(prod[i].rhs)-
1];
break;
}
}
}
}

void main(void)
{
SPM s;
s.inputSPM();
s.printSPM();
s.PrintGrammer();
s.parseString();
s.printParseTable();
getch();
}

/*cout << "\n How many symbols: ";


cin >> no_symb;
cout << "\n Enter " << no_symb << " symbols:\n";

for(i=0;i<no_symb;i++)
{
cout << "Symbol" << i+1 << ":";
cin >> symb[i];
}
symb[no_symb]='\0';

cout << endl;


for(i=0;i<no_symb;i++)
cout << "\t" << symb[i];
cout << endl;

for(i=0;i<no_symb;i++)
{
cout << symb[i];
for(j=0;j<no_symb;j++)
{
//cout << "\t";
cin >> spm[i][j];
}
}*/

OUTPUT:

R S T a > ^ , ( )
R 0 0 0 0 0 0 0 = 0
S 0 0 0 0 0 0 = > 0
T 0 0 0 0 0 0 0 > 0
a 0 0 0 0 0 > 0 > >
^ 0 0 0 0 0 > 0 > >
, 0 < = < < 0 < 0 0
( = < < < < 0 < 0 0
) 0 0 0 0 0 > 0 > >
$ 0 0 0 < < 0 < 0 0

START STATE : S
Non Terminlas :
NT1 R
NT2 S
NT3 T

Terminals :
T1 : a
T2 : ^
T3 : ,
T4 : (
T5 : )
T6 : $

Productions :
Production No 1 S->a
Production No 2 S->^
Production No 3 S->(R)
Production No 4 T->S,T
Production No 5 T->S
Production No 6 R->T

Stack Opr Input12


$ < (a,a)$
$( < a,a)$
$(a < ,a)$

$(S > ,a)$


$(S, = a)$
$(S,a < )$
$(S,S > )$
$(S,T > )$
$(T > )$
$(R > )$
$(R) = $
$S > $
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-I)

PRACTICAL 12

Linearizing a given SPM

Write a C-program which accepts the following SPM and linearizes it to obtain
SPM functions ( f & g ) and display them in suitable format.

INPUT is

OUTPUT is
Program:

// Lenearizing a given SPM


#include<stdio.h>
#include<iostream.h>
#include<conio.h>
#include<ctype.h>
#include<string.h>
#include<stdlib.h>

class SPM
{
int no_symb;
char symb[20];
char ForG;
int FGPath[2][20];
char spm[20][20];
int maxpath;

public:
void inputSPM();
void printSPM();
void findFG();
void printFG();
int findNextPath(int,int,int,char);
};

void SPM :: findFG()


{
int i,j,k,fcounter,gcounter,tracePath=0;

for(i=0;i<no_symb;i++)
{
maxpath=0;
findNextPath(i,0,0,'F');
FGPath[0][i]=maxpath;
}

for(i=0;i<no_symb;i++)
{
maxpath=0;
findNextPath(0,i,0,'G');
FGPath[1][i]=maxpath;
}
}

int SPM :: findNextPath(int f,int g,int path,char FG)


{
int i,j;
if(FG=='F')
{
for(i=0;i<no_symb;i++)
if(spm[f][i]=='>')
{
//path=path+1;
findNextPath(f,i,path+1,'G');
}
if(i==no_symb)
if(path > maxpath)
{
maxpath = path;
return 0;
}
}
else
{
for(i=0;i<no_symb;i++)
if(spm[i][g]=='<')
{
//path=path+1;
findNextPath(i,g,path+1,'F');
}
if(i==no_symb)
if(path > maxpath)
{
maxpath = path;
return 0;
}
}
}

void SPM :: printFG()


{
int i,j;

cout << endl << endl;


for(i=0;i<no_symb;i++)
cout << "\t" << symb[i];

cout << endl << "f";


for(i=0;i<no_symb;i++)
cout << "\t" << FGPath[0][i];

cout << endl << "g";


for(i=0;i<no_symb;i++)
cout << "\t" << FGPath[1][i];
}

void SPM :: inputSPM()


{
int i,j;
clrscr();

no_symb=4;
symb[0]='i';
symb[1]='+';
symb[2]='*';
symb[3]='$';

spm[0][0]='0';
spm[0][1]='>';
spm[0][2]='>';
spm[0][3]='>';
spm[1][0]='<';
spm[1][1]='>';
spm[1][2]='<';
spm[1][3]='>';
spm[2][0]='<';
spm[2][1]='>';
spm[2][2]='>';
spm[2][3]='>';
spm[3][0]='<';
spm[3][1]='<';
spm[3][2]='<';
spm[3][3]='0';

/*cout << "\n How many symbols: ";


cin >> no_symb;
cout << "\n Enter " << no_symb << " symbols:\n";

for(i=0;i<no_symb;i++)
{
cout << "Symbol" << i+1 << ":";
cin >> symb[i];
}
symb[no_symb]='\0';

cout << endl;


for(i=0;i<no_symb;i++)
cout << "\t" << symb[i];
cout << endl;

for(i=0;i<no_symb;i++)
{
cout << symb[i];
for(j=0;j<no_symb;j++)
{
//cout << "\t";
cin >> spm[i][j];
}
}*/
}

void SPM :: printSPM()


{
int i,j;

cout << endl << "\t";


for(i=0;i<no_symb;i++)
cout << symb[i] << "\t";

for(i=0;i<no_symb;i++)
{
cout << endl << symb[i];
for(j=0;j<no_symb;j++)
cout << "\t" << spm[i][j];
}
}

int main(void)
{
SPM s;
s.inputSPM();
s.printSPM();
s.findFG();
s.printFG();
getch();
return 0;
}

OUTPUT:

i + * $
i 0 > > >
+ < > < >
* < > > >
$ < < < 0

i + * $
f 4 2 4 0
g 5 1 3 0
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-I)

PRACTICAL 13

Parsing using Simple Precedence Functions

Write a C-program which accepts the following Simple Precedence Functions


and parse the strings given below and display them.

INPUT is

Parse the following strings :

1) b ( aa ) b
2) b ( ( aa ) a ) b
3) b ( ( aaa) a ) b
PROGRAM

// SPM parsing using SPM functions


#include<stdio.h>
#include<iostream.h>
#include<conio.h>
#include<ctype.h>
#include<string.h>
#include<stdlib.h>

class FGTable
{
int no_symb;
char symb[20];
int FPath[20],GPath[20];

int no_nt;
char NT[20][10];

int no_t;
char T[20][10];

int no_prod;

struct PRD
{
char lhs[10];
char rhs[20];
}prod[10];

char StartSymbol[10];

char stack[20][20];
char opr[20];
char input[20][20];
char inputString[20];
int parseStep;
int stackMem;

public:
void inputFG();
void printFG();
void parseString();
int getSymbPos(char);
void convInput(int);
void convStack(int);
char InputString[20];
FGTable(void);
void PrintGrammer(void);
void copyInput();
void printParseTable();
};

void FGTable :: printParseTable()


{
int i;

cout << endl << endl << "Stack\tOpr\tInput";


printf("%d",parseStep);
for(i=0;i<parseStep;i++)
cout << endl << stack[i] << "\t" << opr[i] << "\t" << input[i];
}

void FGTable :: PrintGrammer(void)


{
cout<<"\nSTART STATE : "<<StartSymbol;

cout<<"\nNon Terminlas : ";


for(int i=0; i<no_nt; ++i )
cout<<"\nNT"<<i+1<<" "<<NT[i];

cout<<"\nTerminals : ";
for(i=0; i<no_t; ++i )
cout<<"\nT"<<i+1<<" : "<< T[i];

cout << "\nProductions : ";


for(i=0;i<no_prod;++i)
{
cout<<"\nProduction No "<<i+1<<" "<<prod[i].lhs<<"->" ;
cout<<prod[i].rhs;
}

getch();
}

FGTable :: FGTable(void)
{
clrscr();
parseStep=0;
}

int FGTable :: getSymbPos(char symbol)


{
int i;
for(i=0;i<no_symb;i++)
if(symb[i] == symbol)
return i;
}

void FGTable :: parseString()


{
char temp,*startSymCheck;

parseStep=0;
strcpy(stack[0],"$");
opr[0]='<';
strcpy(input[0],inputString);
strcat(input[0],"$");
strcpy(startSymCheck,"$");
strcat(startSymCheck,StartSymbol);
stackMem=0;

while(strcmp(input[parseStep],"$") != 0 || strcmp(stack[parseStep],"$") != 0)
{
parseStep++;
strcpy(input[parseStep],input[parseStep-1]);
strcpy(stack[parseStep],stack[parseStep-1]);

if(strcmp(stack[parseStep],startSymCheck) == 0)
break;

if(FPath[getSymbPos(stack[parseStep][stackMem])] <=
GPath[getSymbPos(input[parseStep][0])])
{
if(FPath[getSymbPos(stack[parseStep][stackMem])] <
GPath[getSymbPos(input[parseStep][0])])
opr[parseStep]='<';
else
opr[parseStep]='=';

temp = input[parseStep][0];
convInput(parseStep);
stack[parseStep][++stackMem] = temp;
stack[parseStep][stackMem+1] = '\0';
}
else
{
opr[parseStep]='>';
convStack(parseStep);
}
}
}

void FGTable :: copyInput()


{
int i;
for(i=0;i<strlen(inputString);i++)
input[0][i]=inputString[i];
input[0][i]='\0';
}
void FGTable :: convInput(int step)
{
int i;
for(i=0;i<strlen(input[step]);i++)
input[step][i]=input[step][i+1];
}

void FGTable :: convStack(int step)


{
int i,startPos,j;
char *substr;
char change='y';

for(i=0;i<no_prod;i++)
if((substr=strstr(stack[step],prod[i].rhs)) != NULL)
{
startPos=substr-stack[step];

if(strlen(stack[step]) == strlen(prod[i].rhs) + startPos)


{
stackMem = stackMem - strlen(prod[i].rhs) + 1;
stack[step][startPos]=prod[i].lhs[0];
for(j = startPos+1 ; j < startPos + strlen(prod[i].rhs) ; j++)
stack[step][j]=stack[step][j+strlen(prod[i].rhs)-
1];
}
}
}

void FGTable :: printFG()


{
int i,j;

cout << endl << endl;


for(i=0;i<no_symb;i++)
cout << "\t" << symb[i];

cout << endl << "f";


for(i=0;i<no_symb;i++)
cout << "\t" << FPath[i];

cout << endl << "g";


for(i=0;i<no_symb;i++)
cout << "\t" << GPath[i];
}

void FGTable :: inputFG()


{
int i,j;
clrscr();

no_symb=8;
symb[0]='Z';
symb[1]='M';
symb[2]='L';
symb[3]='a';
symb[4]='b';
symb[5]='(';
symb[6]=')';
symb[7]='$';

FPath[0]=1;
FPath[1]=7;
FPath[2]=8;
FPath[3]=9;
FPath[4]=4;
FPath[5]=2;
FPath[6]=8;
FPath[7]=0;

GPath[0]=1;
GPath[1]=4;
GPath[2]=2;
GPath[3]=7;
GPath[4]=7;
GPath[5]=5;
GPath[6]=9;
GPath[7]=0;

no_nt = 3;
strcpy( NT[0], "Z");
strcpy( NT[1], "M");
strcpy( NT[2], "L");

no_t = 4;
strcpy( T[0] ,"a");
strcpy( T[1] , "b");
strcpy( T[2] , "(");
strcpy( T[3] , ")");

no_prod = 4;
strcpy( prod[0].lhs , "Z");
strcpy( prod[0].rhs , "bMb");

strcpy( prod[1].lhs , "M");


strcpy( prod[1].rhs , "(L");

strcpy( prod[2].lhs , "M");


strcpy( prod[2].rhs , "a");
strcpy( prod[3].lhs , "L");
strcpy( prod[3].rhs , "Ma)");

strcpy( StartSymbol , "Z");

strcpy(inputString,"b(aa)b");
}

void main(void)
{
FGTable f;
f.inputFG();
f.printFG();
f.parseString();
f.printParseTable();
getch();
}

OUTPUT:

Z M L a b ( ) $
f 1 7 8 9 4 2 8 0
g 1 4 2 7 7 5 9 0

Stack Opr Input


$ < b(aa)b$
$b < (aa)b$
$b( < aa)b$
$b(a < a)b$
$b(M > a)b$
$b(Ma = )b$
$b(Ma) = b$
$b(L > b$
$bM > b$
$bMb = $
$Z > $
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-I)

PRACTICAL 14

Operator Precedence grammar ( OPM )

You have been given the following rules to obtain the ‘Less Than’ & ‘Greater
Than’ Matrices.

Less Than -> ( FIRST ) * ( FIRST TERM )


Greater Than -> ( LAST * ) (LAST TERM ) T ( )
Write a C-program to extract the FIRST, EQUAL, LAST,
FIRST_TERM, EQUAL_TERM & LAST_TERM matrices from the following
Grammar. By using superimposition of the three matrices obtain & print the
OPM.

Grammar G : { N, T, P, S }

Production is E -> E + T / T

T -> T * F / F

F -> ( E ) / id
PROGRAM:

#include<iostream.h>
#include<stdio.h>
#include<conio.h>
#include<graphics.h>
#include<stdlib.h>
#include<alloc.h>
#include<string.h>

class opm
{
private:
char s[20],cnt[10],ct[10],**p1,**prod,**lval,**rval;
int meq[10][10],mfplus[10][10],mfstar[10][10],ml[10][10];
int c,i,cp,t,j,nt,n,k,l;
int m3[10][10],m[10][10],mfterm[10][10],mlterm[10][10],mltr[10][10];
int eq[10][10];
char sim[10][10];
public:
void get_data();
void display(int m[10][10]);
void equal();
void first();
void last();
void multiply(int m1[10][10],int m2[10][10]);
void superimpose();
void parse();
void fterm();
void lterm();
void less();
void pequal();
void greater();
void matrix();
void simpose();
};

void opm::get_data()
{
cout<<"\nHow many nonterminals:";
cin>>nt;
cout<<"\nEnter nonterminals:";
for(i=0;i<nt;i++)
cin>>cnt[i];
cout<<"\nHow many terminals:";
cin>>t;
cout<<"\nEnter terminals:";
for(i=0;i<t;i++)
cin>>ct[i];
//i=i+1;
ct[i]='#';
t=t+1;
cout<<"\nHow many productions:";
cin>>cp;
int n1=0;
lval=(char **)malloc(sizeof(char)*10);
rval=(char **)malloc(sizeof(char)*10);
for(n1=0;n1<cp;n1++)
{
lval[n1]=(char *)malloc(sizeof(char)*10);
rval[n1]=(char *)malloc(sizeof(char)*10);
}
prod[n1]=(char *)malloc(sizeof(char)*10);
for(n1=0;n1<cp;n1++)
prod[n1]=(char *)malloc(sizeof(char)*10);
for(k=0;k<cp;k++)
{
cout<<"\nEnter the production:";
gets(prod[k]);
p1[k]=strtok(prod[k]," ");
lval[k]=strtok(p1[k],"=");
rval[k]=strtok(NULL," ");
}
for(k=0;k<nt;k++)
s[k]=cnt[k];
l=k;
k=0;
while(ct[k]!='\0')
{
s[l]=ct[k];
k++;
l++;
cout<<"\t"<<s[l];
}
}

void opm::matrix()
{
for(i=0;i<t+nt;i++)
{
for(j=0;j<t+nt;j++)
{
meq[i][j]=0;
mfplus[i][j]=0;
mfstar[i][j]=0;
ml[i][j]=0;
mfterm[i][j]=0;
mlterm[i][j]=0;
mltr[i][j]=0;
m3[i][j]=0;
eq[i][j]=0;
sim[i][j]='0';
}
}
}

void opm::equal()
{
char s1,s2;
int x=0,y=0,a=0,b=0;
clrscr();
for(k=0;k<cp;k++)
{
if(strlen(rval[k])>1)
{
for(l=0;l<strlen(rval[k]);l++)
{
s1=rval[k][l];
if(rval[k][++l]!=NULL)
s2=rval[k][l];
else
break;
x=y=0;
while(s[x]!='\0')
{
if(s[x]==s1)
{
a=x;
break;
}
x++;
}//while

while(s[y]!='\0')
{
if(s[y]==s2)
{
b=y;
break;
}
y++;
}//while
meq[a][b]=1;
l--;
}//for
}//if
}//for
cout<<"Equal :\n";
display(meq);
}

void opm::first()
{
char f1,f2;
int x=0,y=0,a=0,b=0;
n=t+nt;
for(k=0;k<cp;k++)
{
f1=lval[k][0];
f2=rval[k][0];
x=y=0;
while(s[x]!='\0')
{
if(s[x]==f1)
{
a=x;
break;
}//if
x++;
}//while
while(s[y]!='\0')
{
if(s[y]==f2)
{
b=y;
break;
}
y++;
}
mfplus[a][b]=1;
}

int i1=0;
while(i1<n)
{
for(int j2=0;j2<n;j2++)
{
if(mfplus[j2][i1]==1)
{
for(int k2=0;k2<n;k2++)
mfplus[j2][k2]=(mfplus[j2][k2] || mfplus[i1][k2]);
}//if
}
i1++;
}
for(i=0;i<n;i++)
{
for(j=0;j<n;j++)
mfstar[i][j]=mfplus[i][j];
mfstar[i][i]=1;
}
cout<<"First* :\n";
display(mfstar);
}

void opm::fterm()
{
flushall();
char s1,s2;
int flag=0;
int x=0,y=0,a=0,b=0,k1=0;
for(k1=0;k1<cp;k1++)
{
flag=0;
if(strlen(rval[k1])==1)
{
for(i=0;i<nt;i++)
{
if(rval[k1][0]==cnt[i])
{
flag=1;
break;
}
}
}
if(flag!=1)
{
s1=lval[k1][0];

for(i=0;i<t;i++)
{
if(rval[k1][0]==ct[i])
s2=rval[k1][0];
else if(rval[k1][1]==ct[i])
s2=rval[k1][1];
}
x=y=0;
while(s[x]!='\0')
{
if(s[x]==s1)
{
a=x;
break;
}//if
x++;
}//while
while(s[y]!='\0')
{
if(s[y]==s2)
{
b=y;
break;
}
y++;
}
mfterm[a][b]=1;
}
}
cout<<"\n Firstterm :";
display(mfterm);
}

void opm::lterm()
{
char l1,l2;
int x=0,y=0,a=0,b=0;
int z,flag1=0;
flushall();
for(k=0;k<cp;k++)
{
flag1=0;
if(strlen(rval[k])==1)
{
for(i=0;i<nt;i++)
{
if(rval[k][0]==cnt[i])
{
flag1=1;
break;
}
else
flag1=0;
}
}
if(flag1!=1)
{
l1=lval[k][0];
z=strlen(rval[k]);
for(i=0;i<t;i++)
{
if(rval[k][z-1]==ct[i])
l2=rval[k][z-1];
else if(rval[k][z-2]==ct[i])
l2=rval[k][z-2];
}
x=y=0;
while(s[x]!='\0')
{
if(s[x]==l1)
{
a=x;
break;
}//if
x++;
}//while
while(s[y]!='\0')
{
if(s[y]==l2)
{
b=y;
break;
}
y++;
} //while
mlterm[a][b]=1;
}//if
}//for
cout<<"Lastterm :\n";
display(mlterm);
}

void opm::last()
{
char l1,l2;
int x=0,y=0,a=0,b=0;
int z;
int n=t+nt;
flushall();
for(k=0;k<cp;k++)
{
l1=lval[k][0];
z=strlen(rval[k]);
l2=rval[k][z-1];
x=y=0;
while(s[x]!='\0')
{
if(s[x]==l1)
{
a=x;
break;
}//if
x++;
}//while
while(s[y]!='\0')
{
if(s[y]==l2)
{
b=y;
break;
}
y++;
} //while
ml[a][b]=1;
}//for
int i1=0;
while(i1<n)
{
for(int j1=0;j1<n;j1++)
{
if(ml[j1][i1]==1)
{
for(int k1=0;k1<n;k1++)
ml[j1][k1]=(ml[j1][k1] || ml[i1][k1]);
}//if
}
i1++;
}
for(i=0;i<n;i++)
{
for(j=0;j<n;j++)
ml[i][i]=1;
}

cout<<"Last * :\n";
display(ml);
}

void opm::greater()
{
int n=t+nt;
for(i=0;i<n;i++)
for(j=0;j<n;j++)
m3[i][j]=0;
multiply(ml,mlterm);
for(i=0;i<n;i++)
for(j=0;j<n;j++)
ml[i][j]=0;
for(i=0;i<n;i++)
{
for(j=0;j<n;j++)
ml[j][i]=m3[i][j];
}
for(i=0;i<n;i++)
for(j=0;j<n;j++)
m3[i][j]=0;
multiply(ml,meq);
for(i=0;i<n;i++)
for(j=0;j<n;j++)
mltr[i][j]=m3[i][j];
cout<<"\nGreater Matrix : ";
display(mltr);
}

void opm::less()
{
int n=t+nt;
multiply(meq,mfstar);
for(i=0;i<n;i++)
for(j=0;j<n;j++)
mfstar[i][j]=0;
for(i=0;i<n;i++)
{
for(j=0;j<n;j++)
mfstar[i][j]=m3[i][j];
}
for(i=0;i<n;i++)
for(j=0;j<n;j++)
m3[i][j]=0;
multiply(mfstar,mfterm);
for(i=0;i<n;i++)
{
for(j=0;j<n;j++)
mfstar[i][j]=0;
}
for(i=0;i<n;i++)
{
for(j=0;j<n;j++)
mfstar[i][j]=m3[i][j];
}
cout<<"\n Less Matrix :";
display(mfstar);
}

void opm::pequal()
{
int i1,j1,i2,i3,k1,x,y,a,b;
char l,m;
for(j1=0;j1<cp;j1++)
{
for(k1=0;k1<strlen(rval[j1]);k1++)
{
l=m='\0';
a=b=0;
for(i1=0;i1<t;i1++)
if(rval[j1][k1]==ct[i1])
{
l=rval[j1][k1];
for(i2=0;i2<t;i2++)
if(rval[j1][k1+1]==ct[i2])
{
m=rval[j1][k1+1];
break;
}
else if(rval[j1][k1+2]==ct[i2])
for(i3=0;i3<t;i3++)
if(rval[j1][k1+2]==ct[i3])
{
m=rval[j1][k1+2];
break;
}
}//if
if(l!='\0' && m!='\0')
{
x=y=0;
while(s[x]!='\0')
{
if(s[x]==l)
{
a=x;
break;
}//if

x++;
}//while
while(s[y]!='\0')
{
if(s[y]==m)
{
b=y;
break;
}
y++;
} //while
eq[a][b]=1;
a=b=0;
}//if

}
}
cout<<"\nEqual precedence:";
display(eq);
}

void opm::multiply(int m1[10][10],int m2[10][10])


{
int n=t+nt;
for(i=0;i<n;i++)
{
for(j=0;j<n;j++)
{
for(int k=0;k<n;k++)
m3[i][j]=m3[i][j] + m1[i][k] * m2[k][j];
if(m3[i][j]>=2)
m3[i][j]=1;
}
}
}

void opm::simpose()
{
int a,b,c;
a=nt+t;
for(i=0;i<a;i++)
for(j=0;j<a;j++)
{
sim[i][j]='0';
m[i][j]=0;
}

for(i=a-t;i<a;i++)
{
m[i][a-1]=3;
m[a-1][i]=2;
}
for(i=0;i<a;i++)
{
for(j=0;j<a;j++)
{
if(mfstar[i][j]==1)
{
sim[i][j]='<';
m[i][j]=2;
}
if(mltr[i][j]==1)
{
sim[i][j]='>';
m[i][j]=3;
}
if(eq[i][j]==1)
{
sim[i][j]='=';
m[i][j]=1;
}
}
}
display(m);
cout<<"\nSuperimposed matrix:";
cout<<"\n";
for(i=0;i<a;i++)
cout<<"\t"<<s[i];
cout<<"\n ----------------------------------------------------------------";
for(i=0;i<a;i++)
{
cout<<"\n "<<s[i];
cout<<" |";
for(j=0;j<a;j++)
cout<<"\t"<<sim[i][j];
}
}

void opm::parse()
{
char c;
int q=0,m1=0,k=0,v,w;
char p[15],hand[10];
int a,b,fh=-1,bh=-1,inh=0,e=1;
int flag=0;
cout<<"\nEnter the string to be parsed:";
gets(p);
cout<<"\n Enter the exclusive symbol :";
cin>>c;
q=strlen(p);
m1=0;
while(m1<q)
{
// a=b=0;
/* if(p[m1]=='#')
{
a=1;
flag=1;
v=w=0;
}*/
for(k=0;k<t;k++)
if(p[m1]==ct[k])
v=w=0;
if(flag==0)
{
a=b=0;
while(s[v]!='\0')
{
if(s[v]==p[m1])
{
a=v;
flag=1;
break;
}
v++;
}
}
if(flag==1)
{
m1++;
for(k=0;k<t;k++)
if(p[m1]==ct[k])
{
while(s[w]!='\0')

{
if(s[w]==p[m1])
{
b=w;
flag=0;
// m1--;
break;
}
w++;
}//while
}//if
// m1--;
}//if
if(a!=0 && b!=0)
{
switch(m[a][b])
{
case 2:

{
for(int k1=0;k1<nt;k1++)
{
if(p[m1-1]==cnt[k1])
{
fh=m1-1;
break;
}
else
{
fh=m1;
// break;
}
}
break;
}
case 3: bh=m1-1; break;
case 1: e++;
}//switch
if(fh>=0 && bh>0)
{
inh=fh;
for(k=0;fh<=bh;fh++,k++)
hand[k]=p[fh];
hand[k]='\0';
cout<<"\nHandle:"<<hand;
for(k=0;k<cp;k++)
{
if(strcmp(rval[k],hand)==0)
{
p[inh]=lval[k][0];
break;
}
}
for(;p[bh]!='\0';)
p[++inh]=p[++bh];
p[bh]='\0';
a=b=0;
cout<<"\n P:"<<p;
fh=bh=e=m1=-1;
}//if
}//if a,b
if(a==0)
m1++;
if(p[1]==c &&strlen(p)==3)
break;
}//while
for(k=0;k<cp;k++)
if(strcmp(rval[k],hand)==0)
break;
if(c==lval[k][0])
cout<<"\nString is parsable"<<lval[k][0];
else
cout<<"\nString is not parsable";
}
void opm::display(int m[10][10])
{
cout<<"\n\n";
flushall();
int p=t+nt;
for(i=0;i<p;i++)
cout<<"\t"<<s[i];
cout<<"\n ------------------------------------------------------------------";
for(i=0;i<p;i++)
{
cout<<"\n "<<s[i];
cout<<" |";
for(j=0;j<p;j++)
cout<<"\t"<<m[i][j];
}
}
void main()
{
opm o1;
int a;
clrscr();
flushall();
o1.get_data();
o1.matrix();
o1.equal();
getch();
clrscr();
o1.first();
getch();
clrscr();
o1.last();
getch();
clrscr();
o1.fterm();
getch();
clrscr();
o1.lterm();
getch();
clrscr();
o1.less();
getch();
clrscr();
o1.greater();
getch();
clrscr();
o1.pequal();
getch();
clrscr();
o1.simpose();
getch();
clrscr();
o1.parse();
getch();
}
OUTPUT-

Program Input:-

How many nonterminals:3


Enter nonterminals:ETF
How many terminals:5
Enter terminals:+*()i
How many productions:6
Enter the production:E=E+T
Enter the production:T=T*F
Enter the production:E=T
Enter the production:T=F
Enter the production:F=(E)
Enter the production:F=i

Program Output:-

Equal :
E T F + * ( ) i #
------------------------------------------------------------------
E| 0 0 0 1 0 0 1 0 0
T| 0 0 0 0 1 0 0 0 0
F| 0 0 0 0 0 0 0 0 0
+| 0 1 0 0 0 0 0 0 0
*| 0 0 1 0 0 0 0 0 0
(| 1 0 0 0 0 0 0 0 0
)| 0 0 0 0 0 0 0 0 0
i| 0 0 0 0 0 0 0 0 0
#| 0 0 0 0 0 0 0 0 0

First* :
E T F + * ( ) i #
------------------------------------------------------------------
E| 1 1 1 0 0 1 0 1 0
T| 0 1 1 0 0 1 0 1 0
F| 0 0 1 0 0 1 0 1 0
+| 0 0 0 1 0 0 0 0 0
*| 0 0 0 0 1 0 0 0 0
(| 0 0 0 0 0 1 0 0 0
)| 0 0 0 0 0 0 1 0 0
i| 0 0 0 0 0 0 0 1 0
#| 0 0 0 0 0 0 0 0 1
Last * :
E T F + * ( ) i #
------------------------------------------------------------------
E| 1 1 1 0 0 0 1 1 0
T| 0 1 1 0 0 0 1 1 0
F| 0 0 1 0 0 0 1 1 0
+| 0 0 0 1 0 0 0 0 0
*| 0 0 0 0 1 0 0 0 0
(| 0 0 0 0 0 1 0 0 0
)| 0 0 0 0 0 0 1 0 0
i| 0 0 0 0 0 0 0 1 0
#| 0 0 0 0 0 0 0 0 1

Firstterm :
E T F + * ( ) i #
------------------------------------------------------------------
E| 0 0 0 1 0 0 0 0 0
T| 0 0 0 0 1 0 0 0 0
F| 0 0 0 0 0 1 0 1 0
+| 0 0 0 0 0 0 0 0 0
*| 0 0 0 0 0 0 0 0 0
(| 0 0 0 0 0 0 0 0 0
)| 0 0 0 0 0 0 0 0 0
i| 0 0 0 0 0 0 0 0 0
#| 0 0 0 0 0 0 0 0 0

Lastterm :
E T F + * ( ) i #
------------------------------------------------------------------
E| 0 0 0 1 0 0 0 0 0
T| 0 0 0 0 1 0 0 0 0
F| 0 0 0 0 0 0 1 1 0
+| 0 0 0 0 0 0 0 0 0
*| 0 0 0 0 0 0 0 0 0
(| 0 0 0 0 0 0 0 0 0
)| 0 0 0 0 0 0 0 0 0
i| 0 0 0 0 0 0 0 0 0
#| 0 0 0 0 0 0 0 0 0
Less Matrix :
E T F + * ( ) i #
------------------------------------------------------------------
E| 0 0 0 0 0 0 0 0 0
T| 0 0 0 0 0 0 0 0 0
F| 0 0 0 0 0 0 0 0 0
+| 0 0 0 0 1 1 0 1 0
*| 0 0 0 0 0 1 0 1 0
(| 0 0 0 1 1 1 0 1 0
)| 0 0 0 0 0 0 0 0 0
i| 0 0 0 0 0 0 0 0 0
#| 0 0 0 0 0 0 0 0 0

Greater Matrix :
E T F + * ( ) i #
------------------------------------------------------------------
E| 0 0 0 0 0 0 0 0 0
T| 0 0 0 0 0 0 0 0 0
F| 0 0 0 0 0 0 0 0 0
+| 0 0 0 1 0 0 1 0 0
*| 0 0 0 1 1 0 1 0 0
(| 0 0 0 0 0 0 0 0 0
)| 0 0 0 1 1 0 1 0 0
i| 0 0 0 1 1 0 1 0 0
#| 0 0 0 0 0 0 0 0 0

Equal precedence:
E T F + * ( ) i #
------------------------------------------------------------------
E| 0 0 0 0 0 0 0 0 0
T| 0 0 0 0 0 0 0 0 0
F| 0 0 0 0 0 0 0 0 0
+| 0 0 0 0 0 0 0 0 0
*| 0 0 0 0 0 0 0 0 0
(| 0 0 0 0 0 0 1 0 0
)| 0 0 0 0 0 0 0 0 0
i| 0 0 0 0 0 0 0 0 0
#| 0 0 0 0 0 0 0 0 0
E T F + * ( ) i #
------------------------------------------------------------------
E| 0 0 0 0 0 0 0 0 0
T| 0 0 0 0 0 0 0 0 0
F| 0 0 0 0 0 0 0 0 0
+| 0 0 0 3 2 2 3 2 3
*| 0 0 0 3 3 2 3 2 3
(| 0 0 0 2 2 2 1 2 3
)| 0 0 0 3 3 0 3 0 3
i| 0 0 0 3 3 0 3 0 3
#| 0 0 0 2 2 2 2 2 2

Superimposed matrix:
E T F + * ( ) i #
----------------------------------------------------------------
E| 0 0 0 0 0 0 0 0 0
T| 0 0 0 0 0 0 0 0 0
F| 0 0 0 0 0 0 0 0 0
+| 0 0 0 > < < > < 0
*| 0 0 0 > > < > < 0
(| 0 0 0 < < < = < 0
)| 0 0 0 > > 0 > 0 0
i| 0 0 0 > > 0 > 0 0
#| 0 0 0 0 0 0 0 0 0

Enter the string to be parsed:#T*(E+T)#

Enter the exclusive symbol :T

Handle:E+T
P:#T*(E)#
Handle:(E)
P:#T*F#
Handle:T*F
P:#T#
String is parsableT
NAAC Accreditation “A” Grade
Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07
Compiler Construction ( Section–II )
INDEX

No
Title Page No. Date Sign
.
1 Three Address Code

2 Quadruple Representation

3 Triple Representation

4 Optimize the Quadruples

5 Indirect Triple Representation

6 DAG

7 Construct Natural Loop

8 Live Variable Analysis

9 Depth Spanning Tree

10 Code Generation

11 Postfix to Infix

12 Infix to Postfix
Read the program in file & find out
13
the token in the program.
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-II)

PRACTICAL 1

Three – Address Code

Write a program to obtain Three - Address code for the following arithmetic operation
:
a*b*(c*d)
First Step in generation of the 3 address code of the operation is A=c * d
obtain the operation a * b * A is a temporary variable.
PROGRAM:

// Quadraples and Triples


#include<stdio.h>
#include<iostream.h>
#include<conio.h>
#include<ctype.h>
#include<string.h>
#include<stdlib.h>

class Grammer
{
struct qdrplr
{
char op;
char A1;
char A2;
int R;
} quadraple[10];

struct tripl
{
char op;
char A1;
char A2;
} triple[10];

int no_qdrpl;
int result;

public:
char *inputString;
int res;
char operators[20];
int no_op;
char variables[20];
int no_var;
Grammer(void);
void findQuadra();
int findOpenBrace(char*,int);
int findCloseBrace(char*,int);
char* subString(char*,int,int);
void printQuadra(void);
};

void Grammer :: printQuadra(void)


{
int i;
cout << endl << "Three Address Code:" << endl;
for(i=0;i<no_qdrpl;i++)
{
if(quadraple[i].op != '=')
cout << "T" << quadraple[i].R << " = ";

if(quadraple[i].A1 >= '0' && quadraple[i].A1 <= '9')


cout << "T" << quadraple[i].A1 << " ";
else
cout << quadraple[i].A1 << " ";

cout << quadraple[i].op << " ";

if(quadraple[i].A2 >= '0' && quadraple[i].A2 <= '9')


cout << "T" << quadraple[i].A2 << " ";
else
cout << quadraple[i].A2 << " ";

cout << endl;

}
}

char* Grammer :: subString(char *str, int start, int end)


{
char* returnStr;
int k,l=0;

for(k=start;k<=end;k++)
returnStr[l++] = str[k];
returnStr[l] = '\0';
return returnStr;
}

void Grammer :: findQuadra()


{
int posOpenBrace,posCloseBrace,startExpr,endExpr;
int i,k,l;
char *subStr;

while(strlen(inputString) > 1)
{
startExpr=0;
endExpr=strlen(inputString);

posOpenBrace = findOpenBrace(inputString,0);
if(posOpenBrace != -1)
posCloseBrace = findCloseBrace(inputString,posOpenBrace);

if(posOpenBrace == -1) // no any bracket in string


{
for(k=0;k<strlen(inputString);k++)
{
if(inputString[k]=='*' || inputString[k]=='/' ||
inputString[k]=='%')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}

for(k=0;k<strlen(inputString);k++)
{
if(inputString[k]=='+' || inputString[k]=='-')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}

for(k=0;k<strlen(inputString);k++)
{
if(inputString[k]=='=')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}
}

if(posCloseBrace == posOpenBrace+4) // omly one expr in brackets


{
startExpr=posOpenBrace;
endExpr=posCloseBrace;
goto getQuadra;
}

if(posOpenBrace != -1) // no any bracket in string


{
for(k=posOpenBrace;k<posCloseBrace;k++)
{
if(inputString[k]=='*' || inputString[k]=='/' ||
inputString[k]=='%')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}

for(k=posOpenBrace;k<posCloseBrace;k++)
{
if(inputString[k]=='+' || inputString[k]=='-')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}

for(k=posOpenBrace;k<posCloseBrace;k++)
{
if(inputString[k]=='=')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}
}

getQuadra:

if( inputString[startExpr]=='(' && inputString[endExpr]==')' ) // only one expr


in brackets
{
quadraple[no_qdrpl].A1 = inputString[startExpr+1];
quadraple[no_qdrpl].op = inputString[startExpr+2];
quadraple[no_qdrpl].A2 = inputString[startExpr+3];
quadraple[no_qdrpl].R = result++;

if(inputString[startExpr+1] >= '0' && inputString[startExpr+1] <= '9')


triple[no_qdrpl].A1 = inputString[startExpr+1]-1;
else
triple[no_qdrpl].A1 = inputString[startExpr+1];

triple[no_qdrpl].op = inputString[startExpr+2];

if(inputString[startExpr+3] >= '0' && inputString[startExpr+3] <= '9')


triple[no_qdrpl].A2 = inputString[startExpr+3]-1;
else
triple[no_qdrpl].A2 = inputString[startExpr+3];

no_qdrpl++;
}
else
{
quadraple[no_qdrpl].A1 = inputString[startExpr];
quadraple[no_qdrpl].op = inputString[startExpr+1];
quadraple[no_qdrpl].A2 = inputString[startExpr+2];
quadraple[no_qdrpl].R = result++;

if(inputString[startExpr] >= '0' && inputString[startExpr] <= '9')


triple[no_qdrpl].A1 = inputString[startExpr]-1;
else
triple[no_qdrpl].A1 = inputString[startExpr];

triple[no_qdrpl].op = inputString[startExpr+1];

if(inputString[startExpr+2] >= '0' && inputString[startExpr+2] <= '9')


triple[no_qdrpl].A2 = inputString[startExpr+2]-1;
else
triple[no_qdrpl].A2 = inputString[startExpr+2];

no_qdrpl++;
}

strcpy(subStr,"");
l=0;
k=0;
while(inputString[k] != '\0')
{
if(startExpr == k)
{
subStr[l] = 48+result-1;
k = endExpr+1;
}
else
{
subStr[l] = inputString[k];
k++;
}
l++;
}
subStr[l] = '\0';

strcpy(inputString,subStr);
}
}

int Grammer :: findOpenBrace(char *str,int startPos)


{
int k,currentPos=-1;

for(k=startPos;k<strlen(str);k++)
{
if(str[k] == '(')
currentPos=k;
if(str[k] == ')')
break;
}

return currentPos;
}

int Grammer :: findCloseBrace(char *str,int startPos)


{
int k;

for(k=startPos;k<strlen(str);k++)
if(str[k] == ')')
return k;
return -1;
}

Grammer :: Grammer(void)
{
int i,j;
clrscr();

no_op=0;
no_var=0;
no_qdrpl=0;
result=1;
cout << "Enter the String:";
gets(inputString);
//cout << inputString;

for(i=0;i<strlen(inputString);i++)
{
if(inputString[i] != ' ')
{
if( ((int)inputString[i] >= 65 && (int)inputString[i] <= 90) ||
((int)inputString[i] >= 97 && (int)inputString[i] <= 122) )
{
for(j=0;j<no_var;j++)
if(inputString[i] == variables[j])
goto nextVar;
variables[no_var++] = inputString[i];
nextVar:
}
else
if(inputString[i] == '=' || inputString[i] == '+' || inputString[i]
== '-' || inputString[i] == '*' || inputString[i] == '/' || inputString[i] == '%' || inputString[i] == '('
|| inputString[i] == ')')
{
if(inputString[i] != '(' && inputString[i] != ')')
{
for(j=0;j<no_op;j++)
if(inputString[i] == operators[j])
goto nextOp;
operators[no_op++] = inputString[i];
nextOp:
}
}
else
{
cout << endl << inputString[i] << " is encoutered in the
string as invalid character, Thus the string is invalid.";
getch();
exit(0);
}
}
}

cout << endl << "Variables are as Follows:" << endl;


for(i=0;i<no_var;i++)
cout << variables[i] << " ";

cout << endl << "Operators are as Follows:" << endl;


for(i=0;i<no_op;i++)
cout << operators[i] << " ";
}

int main(void)
{
Grammer g;
//int result;
//G1.PrintGrammer();
//dg.FindFirstFollow();
g.findQuadra();
cout << endl;
g.printQuadra();
getch();
return 0;
}
OUTPUT:

Enter the String:a*b*(c*d)

Variables are as Follows:


abcd
Operators are as Follows:
*

Three Address Code:


T1 = c * d
T2 = a * b
T3 = T2 * T1
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-II)

PRACTICAL 2 & 3

Obtain the Intermediate Representation of the given arithmetic expression in the


Matrix form
a. Quadruple representation of three address statements.
b. Triple representation of three address statements.

Consider the expression : (a+b)*(c+d)


Then it’s Intermediate Representation is,
Quadruple :
OP ARG1 ARG2 RESULT
0 + a B T1
1 + c D T2
2 * T1 T2 T3

Triple :
OP ARG1 ARG2
0 + a B
1 + c D
2 * (0) (1)
Program:

// Quadraples and Triples


#include<stdio.h>
#include<iostream.h>
#include<conio.h>
#include<ctype.h>
#include<string.h>
#include<stdlib.h>

class Grammer
{
struct qdrplr
{
char op;
char A1;
char A2;
int R;
} quadraple[10];

struct tripl
{
char op;
char A1;
char A2;
} triple[10];

int no_qdrpl;
int result;

public:
char *inputString;
int res;
char operators[20];
int no_op;
char variables[20];
int no_var;
Grammer(void);
void findQuadra();
int findOpenBrace(char*,int);
int findCloseBrace(char*,int);
char* subString(char*,int,int);
void printQuadra(void);
};

void Grammer :: printQuadra(void)


{
int i;
cout << endl << "Quadraple Table" << endl;
cout << "\tOP\tA1\tA2\tR" << endl;

for(i=0;i<no_qdrpl;i++)
{
cout << "E" << i << "\t" << quadraple[i].op << "\t" << quadraple[i].A1 << "\t"
<< quadraple[i].A2 << "\t" << quadraple[i].R << endl;
}

cout << endl << "Triple Table" << endl;


cout << "\tOP\tA1\tA2" << endl;

for(i=0;i<no_qdrpl;i++)
{
cout << i << "\t" << triple[i].op << "\t" << triple[i].A1 << "\t" << triple[i].A2
<< endl;
}
}

char* Grammer :: subString(char *str, int start, int end)


{
char* returnStr;
int k,l=0;

for(k=start;k<=end;k++)
returnStr[l++] = str[k];
returnStr[l] = '\0';
return returnStr;
}

void Grammer :: findQuadra()


{
int posOpenBrace,posCloseBrace,startExpr,endExpr;
int i,k,l;
char *subStr;

while(strlen(inputString) > 1)
{
startExpr=0;
endExpr=strlen(inputString);

posOpenBrace = findOpenBrace(inputString,0);
if(posOpenBrace != -1)
posCloseBrace = findCloseBrace(inputString,posOpenBrace);

if(posOpenBrace == -1) // no any bracket in string


{
for(k=0;k<strlen(inputString);k++)
{
if(inputString[k]=='*' || inputString[k]=='/' ||
inputString[k]=='%')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}

for(k=0;k<strlen(inputString);k++)
{
if(inputString[k]=='+' || inputString[k]=='-')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}

for(k=0;k<strlen(inputString);k++)
{
if(inputString[k]=='=')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}
}

if(posCloseBrace == posOpenBrace+4) // omly one expr in brackets


{
startExpr=posOpenBrace;
endExpr=posCloseBrace;
goto getQuadra;
}

if(posOpenBrace != -1) // no any bracket in string


{
for(k=posOpenBrace;k<posCloseBrace;k++)
{
if(inputString[k]=='*' || inputString[k]=='/' ||
inputString[k]=='%')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}
for(k=posOpenBrace;k<posCloseBrace;k++)
{
if(inputString[k]=='+' || inputString[k]=='-')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}

for(k=0;k<strlen(inputString);k++)
{
if(inputString[k]=='=')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}
}

getQuadra:

if( inputString[startExpr]=='(' && inputString[endExpr]==')' ) // only one expr


in brackets
{
quadraple[no_qdrpl].A1 = inputString[startExpr+1];
quadraple[no_qdrpl].op = inputString[startExpr+2];
quadraple[no_qdrpl].A2 = inputString[startExpr+3];
quadraple[no_qdrpl].R = result++;

if(inputString[startExpr+1] >= '0' && inputString[startExpr+1] <= '9')


triple[no_qdrpl].A1 = inputString[startExpr+1]-1;
else
triple[no_qdrpl].A1 = inputString[startExpr+1];

triple[no_qdrpl].op = inputString[startExpr+2];

if(inputString[startExpr+3] >= '0' && inputString[startExpr+3] <= '9')


triple[no_qdrpl].A2 = inputString[startExpr+3]-1;
else
triple[no_qdrpl].A2 = inputString[startExpr+3];

no_qdrpl++;
}
else
{
quadraple[no_qdrpl].A1 = inputString[startExpr];
quadraple[no_qdrpl].op = inputString[startExpr+1];
quadraple[no_qdrpl].A2 = inputString[startExpr+2];
quadraple[no_qdrpl].R = result++;

if(inputString[startExpr] >= '0' && inputString[startExpr] <= '9')


triple[no_qdrpl].A1 = inputString[startExpr]-1;
else
triple[no_qdrpl].A1 = inputString[startExpr];

triple[no_qdrpl].op = inputString[startExpr+1];

if(inputString[startExpr+2] >= '0' && inputString[startExpr+2] <= '9')


triple[no_qdrpl].A2 = inputString[startExpr+2]-1;
else
triple[no_qdrpl].A2 = inputString[startExpr+2];

no_qdrpl++;
}

strcpy(subStr,"");
l=0;
k=0;
while(inputString[k] != '\0')
{
if(startExpr == k)
{
subStr[l] = 48+result-1;
k = endExpr+1;
}
else
{
subStr[l] = inputString[k];
k++;
}
l++;
}
subStr[l] = '\0';

strcpy(inputString,subStr);
}
}

int Grammer :: findOpenBrace(char *str,int startPos)


{
int k,currentPos=-1;

for(k=startPos;k<strlen(str);k++)
{
if(str[k] == '(')
currentPos=k;
if(str[k] == ')')
break;
}

return currentPos;
}

int Grammer :: findCloseBrace(char *str,int startPos)


{
int k;

for(k=startPos;k<strlen(str);k++)
if(str[k] == ')')
return k;
return -1;
}

Grammer :: Grammer(void)
{
int i,j;
clrscr();

no_op=0;
no_var=0;
no_qdrpl=0;
result=1;
cout << "Enter the String:";
gets(inputString);
//cout << inputString;

for(i=0;i<strlen(inputString);i++)
{
if(inputString[i] != ' ')
{
if( ((int)inputString[i] >= 65 && (int)inputString[i] <= 90) ||
((int)inputString[i] >= 97 && (int)inputString[i] <= 122) )
{
for(j=0;j<no_var;j++)
if(inputString[i] == variables[j])
goto nextVar;
variables[no_var++] = inputString[i];
nextVar:
}
else
if(inputString[i] == '=' || inputString[i] == '+' || inputString[i]
== '-' || inputString[i] == '*' || inputString[i] == '/' || inputString[i] == '%' || inputString[i] == '('
|| inputString[i] == ')')
{
if(inputString[i] != '(' && inputString[i] != ')')
{
for(j=0;j<no_op;j++)
if(inputString[i] == operators[j])
goto nextOp;
operators[no_op++] = inputString[i];
nextOp:
}
}
else
{
cout << endl << inputString[i] << " is encoutered in the
string as invalid character, Thus the string is invalid.";
getch();
exit(0);
}
}
}

cout << endl << "Variables are as Follows:" << endl;


for(i=0;i<no_var;i++)
cout << variables[i] << " ";

cout << endl << "Operators are as Follows:" << endl;


for(i=0;i<no_op;i++)
cout << operators[i] << " ";
}

int main(void)
{
Grammer g;
//int result;
//G1.PrintGrammer();
//dg.FindFirstFollow();
g.findQuadra();
cout << endl;
g.printQuadra();
getch();
return 0;
}
OUTPUT:

Enter the String:a=b*(c+d)

Variables are as Follows:


abcd
Operators are as Follows:
=*+

Quadraple Table
OP A1 A2 R
E0 + c d 1
E1 * b 1 2
E2 = a 2 3

Triple Table
OP A1 A2
0 + c d
1 * b 0
2 = a 1
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-II)

PRACTICAL 4

Perform optimization on the quadruples provided to you and generate an


optimized quadruple to produce optimized code for the program.

Consider the expression (a+b)*(a+b)


Then it’s quadruple’s :

Op Arg1 Arg2 Result


0 + a b T1
1 + a b T2
2 * T1 T2 T3

Then it’s optimized quadruple’s

Op Arg1 Arg2 Result


0 + a b T1
1 * T1 T1 T2
PROGRAM:

// Optimization
#include<stdio.h>
#include<iostream.h>
#include<conio.h>
#include<ctype.h>
#include<string.h>
#include<stdlib.h>

class Grammer
{
struct qdrplr
{
char op;
char A1;
char A2;
int R;
} quadraple[10];

struct tripl
{
char op;
char A1;
char A2;
} triple[10];

int no_qdrpl;
int result;

public:
char *inputString;
int res;
char operators[20];
int no_op;
char variables[20];
int no_var;
Grammer(void);
void findQuadra();
int findOpenBrace(char*,int);
int findCloseBrace(char*,int);
char* subString(char*,int,int);
void printQuadra(void);
};

void Grammer :: printQuadra(void)


{
int i;
cout << endl << "Quadraple Table" << endl;
cout << "\tOP\tA1\tA2\tR" << endl;
for(i=0;i<no_qdrpl;i++)
{
cout << "E" << i << "\t" << quadraple[i].op << "\t" << quadraple[i].A1 << "\t" <<
quadraple[i].A2 << "\t" << quadraple[i].R << endl;
}

cout << endl << "Triple Table" << endl;


cout << "\tOP\tA1\tA2" << endl;

for(i=0;i<no_qdrpl;i++)
{
cout << i << "\t" << triple[i].op << "\t" << triple[i].A1 << "\t" << triple[i].A2 <<
endl;
}
}

char* Grammer :: subString(char *str, int start, int end)


{
char* returnStr;
int k,l=0;

for(k=start;k<=end;k++)
returnStr[l++] = str[k];
returnStr[l] = '\0';
return returnStr;
}

void Grammer :: findQuadra()


{
int posOpenBrace,posCloseBrace,startExpr,endExpr;
int i,k,l;
char *subStr;

while(strlen(inputString) > 1)
{
startExpr=0;
endExpr=strlen(inputString);

posOpenBrace = findOpenBrace(inputString,0);
if(posOpenBrace != -1)
posCloseBrace = findCloseBrace(inputString,posOpenBrace);

if(posOpenBrace == -1) // no any bracket in string


{
for(k=0;k<strlen(inputString);k++)
{
if(inputString[k]=='*' || inputString[k]=='/' || inputString[k]=='%')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}

for(k=0;k<strlen(inputString);k++)
{
if(inputString[k]=='+' || inputString[k]=='-')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}
}

if(posCloseBrace == posOpenBrace+4) // omly one expr in brackets


{
startExpr=posOpenBrace;
endExpr=posCloseBrace;
goto getQuadra;
}

if(posOpenBrace != -1) // no any bracket in string


{
for(k=posOpenBrace;k<posCloseBrace;k++)
{
if(inputString[k]=='*' || inputString[k]=='/' || inputString[k]=='%')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}

for(k=posOpenBrace;k<posCloseBrace;k++)
{
if(inputString[k]=='+' || inputString[k]=='-')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}
}

getQuadra:
if( inputString[startExpr]=='(' && inputString[endExpr]==')' ) // only one expr in
brackets
{
for(k=0;k<no_qdrpl;k++)
{
if( (int)quadraple[k].A1 == (int)inputString[startExpr+1] &&
(int)quadraple[k].op == (int)inputString[startExpr+2] &&
(int)quadraple[k].A2 == (int)inputString[startExpr+3])
{
res=k+2;
goto processStr;
}
}

quadraple[no_qdrpl].A1 = inputString[startExpr+1];
quadraple[no_qdrpl].op = inputString[startExpr+2];
quadraple[no_qdrpl].A2 = inputString[startExpr+3];
quadraple[no_qdrpl].R = result++;

if(inputString[startExpr+1] >= '0' && inputString[startExpr+1] <= '9')


triple[no_qdrpl].A1 = inputString[startExpr+1]-1;
else
triple[no_qdrpl].A1 = inputString[startExpr+1];

triple[no_qdrpl].op = inputString[startExpr+2];

if(inputString[startExpr+3] >= '0' && inputString[startExpr+3] <= '9')


triple[no_qdrpl].A2 = inputString[startExpr+3]-1;
else
triple[no_qdrpl].A2 = inputString[startExpr+3];

res=result;
no_qdrpl++;
}
else
{
for(k=0;k<no_qdrpl;k++)
{
if( (int)quadraple[k].A1 == (int)inputString[startExpr] &&
(int)quadraple[k].op == (int)inputString[startExpr+1] &&
(int)quadraple[k].A2 == (int)inputString[startExpr+2])
{
res=k+2;
goto processStr;
}
}

quadraple[no_qdrpl].A1 = inputString[startExpr];
quadraple[no_qdrpl].op = inputString[startExpr+1];
quadraple[no_qdrpl].A2 = inputString[startExpr+2];
quadraple[no_qdrpl].R = result++;

if(inputString[startExpr] >= '0' && inputString[startExpr] <= '9')


triple[no_qdrpl].A1 = inputString[startExpr]-1;
else
triple[no_qdrpl].A1 = inputString[startExpr];

triple[no_qdrpl].op = inputString[startExpr+1];

if(inputString[startExpr+2] >= '0' && inputString[startExpr+2] <= '9')


triple[no_qdrpl].A2 = inputString[startExpr+2]-1;
else
triple[no_qdrpl].A2 = inputString[startExpr+2];

res=result;
no_qdrpl++;
}

processStr:
strcpy(subStr,"");
l=0;
k=0;
while(inputString[k] != '\0')
{
if(startExpr == k)
{
subStr[l] = 48+res-1;
k = endExpr+1;
}
else
{
subStr[l] = inputString[k];
k++;
}
l++;
}
subStr[l] = '\0';

strcpy(inputString,subStr);
}
}

int Grammer :: findOpenBrace(char *str,int startPos)


{
int k,currentPos=-1;

for(k=startPos;k<strlen(str);k++)
{
if(str[k] == '(')
currentPos=k;
if(str[k] == ')')
break;
}

return currentPos;
}

int Grammer :: findCloseBrace(char *str,int startPos)


{
int k;

for(k=startPos;k<strlen(str);k++)
if(str[k] == ')')
return k;
return -1;
}

Grammer :: Grammer(void)
{
int i,j;
clrscr();

no_op=0;
no_var=0;
no_qdrpl=0;
result=1;
cout << "Enter the String:";
gets(inputString);

for(i=0;i<strlen(inputString);i++)
{
if(inputString[i] != ' ')
{
if( ((int)inputString[i] >= 65 && (int)inputString[i] <= 90) ||
((int)inputString[i] >= 97 && (int)inputString[i] <= 122) )
{
for(j=0;j<no_var;j++)
if(inputString[i] == variables[j])
goto nextVar;
variables[no_var++] = inputString[i];
nextVar:
}
else
if(inputString[i] == '+' || inputString[i] == '-' || inputString[i] == '*' ||
inputString[i] == '/' || inputString[i] == '%' || inputString[i] == '(' ||
inputString[i] == ')')
{
if(inputString[i] != '(' && inputString[i] != ')')
{
for(j=0;j<no_op;j++)
if(inputString[i] == operators[j])
goto nextOp;
operators[no_op++] = inputString[i];
nextOp:
}
}
else
{
cout << endl << inputString[i] << " is encoutered in the string as
invalid character, Thus the string is invalid.";
getch();
exit(0);
}
}
}

cout << endl << "Variables are as Follows:" << endl;


for(i=0;i<no_var;i++)
cout << variables[i] << " ";

cout << endl << "Operators are as Follows:" << endl;


for(i=0;i<no_op;i++)
cout << operators[i] << " ";
}

int main(void)
{
Grammer g;
g.findQuadra();
cout << endl;
g.printQuadra();
getch();
return 0;
}
OUTPUT:

Enter the String:(a+b)*(c+d)-(a+b+c)

Variables are as Follows:


abcd

Operators are as Follows:


+*-

Quadraple Table

OP A1 A2 R
E0 + a b 1
E1 + c d 2
E2 + 1 c 3
E3 * 1 2 4
E4 - 4 3 5

Triple Table

OP A1 A2
0 + a b
1 + c d
2 + 0 c
3 * 0 1
4 - 3 2
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-II)

PRACTICAL 5

Indirect Triple Representation

Write a program to obtain indirect triple representation of a following operation

a= - b * ( c + d)

Indirect triple representation is similar to Triple representation but stores the


addresses of instruction in a separate array.
PROGRAM:

// Indirect Triple Representation


#include<stdio.h>
#include<iostream.h>
#include<conio.h>
#include<ctype.h>
#include<string.h>
#include<stdlib.h>

class Grammer
{
struct triple
{
char op;
char A1;
char A2;
} triple[10];

int no_triple;
int result;
int statement[20];

public:
char *inputString;
char operators[20];
int no_op;
char variables[20];
int no_var;
Grammer(void);
void findTriple();
int findOpenBrace(char*,int);
int findCloseBrace(char*,int);
void printTriple(void);
};

void Grammer :: printTriple(void)


{
int i,j;

for(i=0;i<no_triple;i++)
statement[i] = i;

cout << endl << "Triple Table" << endl;

cout << "\tstatement" << endl;


for(i=0;i<no_triple;i++)
cout << i << "\t" << (int)&statement[i] << endl;

cout << endl << endl;


cout << "\tOP\tA1\tA2" << endl;
for(i=0;i<no_triple;i++)
{
cout << (int)&statement[i] << "\t" << triple[i].op << "\t";

if(triple[i].A1 >= '0' && triple[i].A1 <= '9')


{
j = (int)triple[i].A1-48;
cout << (int)&statement[j] << "\t";
}
else
cout << triple[i].A1 << "\t";

if(triple[i].A2 >= '0' && triple[i].A2 <= '9')


{
j = (int)triple[i].A2-48;
cout << (int)&statement[j] << "\t" << endl;
}
else
cout << triple[i].A2 << "\t" << endl;
}
}

void Grammer :: findTriple()


{
int posOpenBrace,posCloseBrace,startExpr,endExpr;
int i,k,l;
char *subStr;

while(strlen(inputString) > 1)
{
startExpr=0;
endExpr=strlen(inputString);

posOpenBrace = findOpenBrace(inputString,0);
if(posOpenBrace != -1)
posCloseBrace = findCloseBrace(inputString,posOpenBrace);

if(posOpenBrace == -1) // no any bracket in string


{
for(k=0;k<strlen(inputString);k++)
{
if(inputString[k]=='*' || inputString[k]=='/' ||
inputString[k]=='%')
{
startExpr=k-1;
endExpr=k+1;
goto getTriple;
}
}

for(k=0;k<strlen(inputString);k++)
{
if(inputString[k]=='+' || inputString[k]=='-')
{
startExpr=k-1;
endExpr=k+1;
goto getTriple;
}
}

for(k=0;k<strlen(inputString);k++)
{
if(inputString[k]=='=')
{
startExpr=k-1;
endExpr=k+1;
goto getTriple;
}
}
}

if(posCloseBrace == posOpenBrace+4) // only one expr in brackets


{
startExpr=posOpenBrace;
endExpr=posCloseBrace;
goto getTriple;
}

if(posOpenBrace != -1) // many expr in bracket


{
for(k=posOpenBrace;k<posCloseBrace;k++)
{
if(inputString[k]=='*' || inputString[k]=='/' ||
inputString[k]=='%')
{
startExpr=k-1;
endExpr=k+1;
goto getTriple;
}
}

for(k=posOpenBrace;k<posCloseBrace;k++)
{
if(inputString[k]=='+' || inputString[k]=='-')
{
startExpr=k-1;
endExpr=k+1;
goto getTriple;
}
}

for(k=posOpenBrace;k<posCloseBrace;k++)
{
if(inputString[k]=='=')
{
startExpr=k-1;
endExpr=k+1;
goto getTriple;
}
}
}

getTriple:

if( inputString[startExpr]=='(' && inputString[endExpr]==')' ) // omly one


expr in brackets
{
triple[no_triple].A1 = inputString[startExpr+1];
triple[no_triple].op = inputString[startExpr+2];
triple[no_triple].A2 = inputString[startExpr+3];
no_triple++;
result++;
}
else
{
triple[no_triple].A1 = inputString[startExpr];
triple[no_triple].op = inputString[startExpr+1];
triple[no_triple].A2 = inputString[startExpr+2];
no_triple++;
result++;
}

strcpy(subStr,"");
l=0;
k=0;
while(inputString[k] != '\0')
{
if(startExpr == k)
{
subStr[l] = 48+result-1;
k = endExpr+1;
}
else
{
subStr[l] = inputString[k];
k++;
}
l++;
}
subStr[l] = '\0';

strcpy(inputString,subStr);
}
}

int Grammer :: findOpenBrace(char *str,int startPos)


{
int k,currentPos=-1;

for(k=startPos;k<strlen(str);k++)
{
if(str[k] == '(')
currentPos=k;
if(str[k] == ')')
break;
}

return currentPos;
}

int Grammer :: findCloseBrace(char *str,int startPos)


{
int k;

for(k=startPos;k<strlen(str);k++)
if(str[k] == ')')
return k;
return -1;
}

Grammer :: Grammer(void)
{
int i,j;
clrscr();

no_op=0;
no_var=0;
no_triple=0;
result=0;
cout << "Enter the String:";
gets(inputString);
//cout << inputString;

for(i=0;i<strlen(inputString);i++)
{
if(inputString[i] != ' ')
{
if( ((int)inputString[i] >= 65 && (int)inputString[i] <= 90) ||
((int)inputString[i] >= 97 && (int)inputString[i] <= 122) )
{
for(j=0;j<no_var;j++)
if(inputString[i] == variables[j])
goto nextVar;
variables[no_var++] = inputString[i];
nextVar:
}
else
if(inputString[i] == '=' || inputString[i] == '+' || inputString[i]
== '-' || inputString[i] == '*' || inputString[i] == '/' || inputString[i] == '%' || inputString[i] == '('
|| inputString[i] == ')')
{
if(inputString[i] != '(' && inputString[i] != ')')
{
for(j=0;j<no_op;j++)
if(inputString[i] == operators[j])
goto nextOp;
operators[no_op++] = inputString[i];
nextOp:
}
}
else
{
cout << endl << inputString[i] << " is encoutered in the
string as invalid character, Thus the string is invalid.";
getch();
exit(0);
}
}
}

cout << endl << "Variables are as Follows:" << endl;


for(i=0;i<no_var;i++)
cout << variables[i] << " ";

cout << endl << "Operators are as Follows:" << endl;


for(i=0;i<no_op;i++)
cout << operators[i] << " ";
}

int main(void)
{
Grammer g;
//int result;
//G1.PrintGrammer();
//dg.FindFirstFollow();
g.findTriple();
cout << endl;
g.printTriple();
getch();
return 0;
}

OUTPUT:

Enter the String:a=b*(c+d)

Variables are as Follows:


abcd
Operators are as Follows:
=*+

Triple Table
statement
0 -96
1 -94
2 -92

OP A1 A2
-96 + c d
-94 * b -96
-92 = a -94
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-II)

PRACTICAL 6

DAG

Write a program which representations a DAG in the form of table with the
fields : Label, Address, identifiers, Left Child, & Right Child for a sequence of
Three Address Code. Input the following Three Address Codes and display the
step by step output of the DAG

A=B+C

B=C+D

D=A
PROGRAM:

#include<stdio.h>
#include<iostream.h>
#include<conio.h>
#include<ctype.h>
#include<string.h>
#include<stdlib.h>

class Dag
{
struct node
{
char label[20],id[20],left[20],right[20];
}dagNode[20];

int noThreeAddCode,noNode;
char code[20][20];

public:
void inputThreeAddCode();
void findDag();
char* subString(char[],int,int);
void addNode(char[]);
};

void Dag :: inputThreeAddCode()


{
noThreeAddCode=3;

strcpy(code[0],"A=B+C");
strcpy(code[1],"B=C+D");
strcpy(code[2],"D=A");
}

void Dag :: addNode(char lbl[])


{
int i;

for(i=0;i<noNode;i++)
{
if(strcmp(dagNode[i].label,lbl) == 0)
goto end;
}
sprintf(dagNode[noNode].label,"%s",lbl);
sprintf(dagNode[noNode].id,"");
sprintf(dagNode[noNode].left,"");
sprintf(dagNode[noNode++].right,"");
end:
}
void Dag :: findDag()
{
int i,j=0;
char *str;
char res[20],op;
char operand1[20],operand2[20];
int eqSpace,opSpace;

noNode=0;
for(i=0;i<noThreeAddCode;i++)
{
strcpy(res,"");
strcpy(operand1,"");
strcpy(operand2,"");
op='n';

str = strchr(code[i],'=');
if(str)
eqSpace=str-code[i];

str = strchr(code[i],'+');
if(str)
{
opSpace=str-code[i];
op='+';
}
else
{
str = strchr(code[i],'-');
if(str)
{
opSpace=str-code[i];
op='-';
}
else
{
str = strchr(code[i],'*');
if(str)
{
opSpace=str-code[i];
op='*';
}
else
{
str = strchr(code[i],'/');
if(str)
{
opSpace=str-code[i];
op='/';
}
else
{
str = strchr(code[i],'%');
if(str)
{
opSpace=str-code[i];
op='%';
}
}
}
}
}

if(op != 'n')
{
strcpy(operand1,subString(code[i],eqSpace+1,opSpace-1));
strcpy(operand2,subString(code[i],opSpace+1,strlen(code[i])-1));
}
else
strcpy(operand1,subString(code[i],eqSpace+1,opSpace-1));
strcpy(res,subString(code[i],0,eqSpace-1));

for(j=0;j<noNode;j++)
{
if(dagNode[j].label[0]==op && strcmp(dagNode[j].left,operand1)==0
&& strcmp(dagNode[j].right,operand2)==0)
{
strcat(dagNode[j].id,",");
strcat(dagNode[j].id,res);
goto next;
}
}

if(op!='n')
{
sprintf(dagNode[noNode].label,"%c",op);
sprintf(dagNode[noNode].id,"%s",res);
sprintf(dagNode[noNode].left,"%s",operand1);
sprintf(dagNode[noNode++].right,"%s",operand2);
addNode(operand1);
addNode(operand2);
}
else
{
for(j=0;j<noNode;j++)
{
if(strstr(dagNode[j].id,operand1) != NULL)
{
strcat(dagNode[j].id,",");
strcat(dagNode[j].id,res);
}
}
}
next:
}

printf("\nLabel\tAddr\tId\tLeft\tRight",dagNode[i].label,&(dagNode[i].label),dagNod
e[i].id,dagNode[i].left,dagNode[i].right);
for(i=0;i<noNode;i++)
printf("\n%s\t%d\t%s\t%s\t%s",dagNode[i].label,&(dagNode[i].label),dagNod
e[i].id,dagNode[i].left,dagNode[i].right);
}

char* Dag :: subString(char *str, int start, int end)


{
char returnStr[20];
int k,l=0;

for(k=start;k<=end;k++)
{
if(str[k] != ' ')
returnStr[l++] = str[k];
}
returnStr[l] = '\0';
return returnStr;
}

void main()
{
Dag d;
clrscr();
d.inputThreeAddCode();
d.findDag();
getch();
}
OUTPUT:

Input Statements
A=B+C
B=C+D
D=A

Label Addr Id Left Right


+ -2014 A,D B C
B -1934
C -1854
+ -1774 B C D
D -1694
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-II)

PRACTICAL 7

Construct Natural Loop

Write a program to create your own data structure to represent a flow – graph.
Write code to construct natural loop from a back edge for the following 5 nodes

Input : -

1->NULL

2->NULL

3->1

4->2

5->4
PROGRAM:

#include<stdio.h>
#include<iostream.h>
#include<conio.h>
#include<ctype.h>
#include<string.h>
#include<stdlib.h>

class Natural
{
int no_node,n,d;
int stack[20],stackMem,loop[20],loopMem;

struct FG
{
int paths;
int endNodes[10];
}flowGraph[20];

public:
void inputFlowGraph();
void printFlowGraph();
void inputBackEdge();
void findNaturalLoop();
void printNaturalLoop();
void insert(int);
};

void Natural :: printNaturalLoop()


{
int i;

cout << "Natural Loop:" << endl;


for(i=0;i<loopMem;i++)
cout << loop[i] << " ";
}

void Natural :: findNaturalLoop()


{
int m,i,j;

stackMem=0;
loopMem=0;
loop[loopMem++]=d;
insert(n);

while(stackMem != 0)
{
m = stack[--stackMem];
for(i=1;i<=no_node;i++)
for(j=0;j<flowGraph[i].paths;j++)
if(flowGraph[i].endNodes[j] == m)
insert(i);
}
}

void Natural :: insert(int node)


{
int i;

for(i=0;i<loopMem;i++)
if(loop[i] == node)
goto endFun;

loop[loopMem++]=node;
stack[stackMem++]=node;

endFun:
}

void Natural :: inputFlowGraph()


{
no_node=10;

flowGraph[1].paths=2;
flowGraph[1].endNodes[0]=2;
flowGraph[1].endNodes[1]=3;

flowGraph[2].paths=1;
flowGraph[2].endNodes[0]=3;

flowGraph[3].paths=1;
flowGraph[3].endNodes[0]=4;

flowGraph[4].paths=3;
flowGraph[4].endNodes[0]=5;
flowGraph[4].endNodes[1]=6;
flowGraph[4].endNodes[2]=3;

flowGraph[5].paths=1;
flowGraph[5].endNodes[0]=7;

flowGraph[6].paths=1;
flowGraph[6].endNodes[0]=7;

flowGraph[7].paths=2;
flowGraph[7].endNodes[0]=8;
flowGraph[7].endNodes[1]=4;
flowGraph[8].paths=3;
flowGraph[8].endNodes[0]=9;
flowGraph[8].endNodes[1]=10;
flowGraph[8].endNodes[2]=3;

flowGraph[9].paths=1;
flowGraph[9].endNodes[0]=1;

flowGraph[10].paths=1;
flowGraph[10].endNodes[0]=7;
}

void Natural :: printFlowGraph()


{
int i,j;

cout << "Node\tpaths" << endl;

for(i=1;i<=no_node;i++)
{
cout << i << "\t";
for(j=0;j<flowGraph[i].paths;j++)
cout << flowGraph[i].endNodes[j] << " ";
cout << endl;
}
}

void Natural :: inputBackEdge()


{
cout << "Your back edge is of type n -> d." << endl;
cout << "Enter n:";
cin >> n;
cout << "Enter d:";
cin >> d;
}

void main()
{
Natural n;
clrscr();
n.inputFlowGraph();
n.printFlowGraph();
n.inputBackEdge();
n.findNaturalLoop();
n.printNaturalLoop();
getch();
}
/*void Natural :: inputFlowGraph()
{
int i,j;

cout << "How many nodes:" << endl;


cin >> no_node;

for(i=0;i<no_node;i++)
{
cout << "For Node " << i+1 << ":" << endl;
cout << "How many paths to other nodes:";
cin >> flowGraph[i].paths;
for(j=0;j<flowGraph[i].paths;j++)
{
cout << "Path " << j+1 << " goes to the node:";
cin >> flowGraph[i].endNodes[j];
}
}
}*/

OUTPUT:

Node paths
1 23
2 3
3 4
4 563
5 7
6 7
7 84
8 9 10 3
9 1
10 7

Your back edge is of type n -> d.


Enter n:10
Enter d:7

Natural Loop:
7 10 8

Your back edge is of type n -> d.


Enter n:9
Enter d:1

Natural Loop:
1 9 8 7 5 6 10 4 3 2
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-II)

PRACTICAL 8

Live Variable Analysis

Write a program to accept a sequence of variables, the IN set for each block of
the flow graph & determine the Live Variables based on the Live – Variable
Analysis algorithm. Output the OUT set – the variables live on exit from each
block of the flow graph.
PROGRAM:

#include<stdio.h>
#include<iostream.h>
#include<conio.h>
#include<ctype.h>
#include<string.h>
#include<stdlib.h>

class LiveVar
{
int DFN[20],dfn_n,dfst_n;
char mark[20];
char change;

struct dfs
{
int startN,endN;
}DFST[30];

struct FG
{
int paths;
int endNodes[10];
}flowGraph[20];

struct DefUse
{
int no_def,no_use;
char def[20];
char use[20];
}du[20];

struct InOut
{
int no_in,no_out;
char in[20];
char out[20];
}inout[20];

public:
int no_node;
void inputFlowGraph();
void printFlowGraph();
void findDFST();
void printDFST();
void search(int);
void findLiveVar();
char* minus(int);
void sort(char*);
};

void LiveVar :: sort(char* str)


{
int i,j;
char temp;

for(i=0;i<strlen(str);i++)
for(j=i+1;j<strlen(str);j++)
if(str[i] > str[j])
{
temp = str[i];
str[i] = str[j];
str[j] = temp;
}
}

char* LiveVar :: minus(int n)


{
char s[20],s1[20],s2[20];
int i,j,k;

strcpy(s,"");
strcat(s,du[n].def);
strcat(s,du[n].use);

for(i=0;i<strlen(s);i++)
for(j=i+1;j<strlen(s);j++)
if(s[i] == s[j] && s[i] != ' ' && s[j]!=' ')
s[j] = ' ';

j=0;
for(i=0;i<=strlen(s);i++)
if(s[i] != ' ')
s1[j++] = s[i];

k=0;
for(i=0;i<strlen(inout[n].out);i++)
{
for(j=0;j<strlen(s1);j++)
if(inout[n].out[i] == s1[j])
goto endLoop;
s2[k++]=inout[n].out[i];
endLoop:
}
s2[k]='\0';

if(strcmp(s2,"")==0)
return s1;
else
return s2;
}

void LiveVar :: findLiveVar()


{
int i,j,k,l,m;
char *str,*str1;

change='y';
for(i=1;i<=no_node;i++)
{
inout[i].no_in=0;
inout[i].no_out=0;
strcpy(inout[i].in,"");
strcpy(inout[i].out,"");
}
clrscr();
again:
if(change!='n')
{
change='n';
for(i=no_node;i>=1;i--)
{
strcpy(str,"");
for(j=0;j<flowGraph[DFN[i]].paths;j++)
strcat(str,inout[flowGraph[DFN[i]].endNodes[j]].in);

if(strcmp(str,"") != 0)
{
for(k=0;k<strlen(str);k++)
for(l=k+1;l<strlen(str);l++)
if(str[k] == str[l] && str[k] != ' ')
str[l] = ' ';
l=0;
for(k=0;k<=strlen(str);k++)
if(str[k] != ' ')
str1[l++] = str[k];
sort(str1);
strcpy(inout[DFN[i]].out,str1);
}

str =minus(DFN[i]);
sort(str);
if(strcmp(inout[DFN[i]].in,str) != 0)
{
change='y';
strcpy(inout[DFN[i]].in,str);
}
}
goto again;
}
}

void LiveVar :: printDFST()


{
int i;

cout << "Depth First Spanning Tree:" << endl;


for(i=0;i<dfst_n;i++)
cout << DFST[i].startN << "->" << DFST[i].endN << endl;
cout << endl;
cout << "Depth First Ordering:" << endl;
for(i=1;i<=no_node;i++)
cout << DFN[i] << " ";

cout << endl << "\nBlock\t\tDEF\t\tUSE\t\tIn\t\tOut\n";


for(i=1;i<=no_node;i++)
cout << i << "\t\t" << du[i].def << "\t\t" << du[i].use << "\t\t" << inout[i].in
<< "\t\t" << inout[i].out << endl;
}

void LiveVar :: findDFST()


{
int m,i,j;

dfst_n = 0;
dfn_n = no_node;

for(i=1;i<=no_node;i++)
mark[i] = 'u';

search(1);
}

void LiveVar :: search(int node)


{
int i;

mark[node] = 'v';

for(i=0;i<flowGraph[node].paths;i++)
if( mark[flowGraph[node].endNodes[i]] == 'u')
{
DFST[dfst_n].startN = node;
DFST[dfst_n++].endN = flowGraph[node].endNodes[i];

search(flowGraph[node].endNodes[i]);
}
DFN[node] = dfn_n;
dfn_n = dfn_n - 1;
}

void LiveVar :: inputFlowGraph()


{
no_node=6;

flowGraph[1].paths=1;
flowGraph[1].endNodes[0]=2;

flowGraph[2].paths=2;
flowGraph[2].endNodes[0]=3;flowGraph[2].endNodes[1]=4;

flowGraph[3].paths=2;
flowGraph[3].endNodes[0]=4;flowGraph[3].endNodes[1]=5;

flowGraph[4].paths=2;
flowGraph[4].endNodes[0]=2;flowGraph[4].endNodes[1]=6;

flowGraph[5].paths=1;
flowGraph[5].endNodes[0]=3;

flowGraph[6].paths=0;

strcpy(du[1].def,"BC");strcpy(du[1].use,"");
strcpy(du[2].def,"AD");strcpy(du[2].use,"ABC");
strcpy(du[3].def,"D");strcpy(du[3].use,"CD");
strcpy(du[4].def,"CE");strcpy(du[4].use,"ABC");
strcpy(du[5].def,"DE");strcpy(du[5].use,"BCE");
strcpy(du[6].def,"BC");strcpy(du[6].use,"BCD");
}

void LiveVar :: printFlowGraph()


{
int i,j;

cout << "Node\tpaths" << endl;

for(i=1;i<=no_node;i++)
{
cout << i << "\t";
for(j=0;j<flowGraph[i].paths;j++)
cout << flowGraph[i].endNodes[j] << " ";
cout << endl;
}
}

void main()
{
LiveVar l;
clrscr();
l.inputFlowGraph();
l.printFlowGraph();
l.findDFST();
l.findLiveVar();
l.printDFST();
getch();
}

OUTPUT:

Depth First Spanning Tree:


1->2
2->3
3->4
4->6
3->5

Depth First Ordering:


123546

Block DEF USE In Out


1 BC E E
2 AD ABC E BDE
3 D CD BE BCDE
4 CE ABC D BCDE
5 DE BCE BCDE BE
6 BC BCD BCD
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-II)

PRACTICAL 9

Depth First Spanning Tree

Write a program to create your own data structure to represent a flow – graph.
Using this structure construct a depth - first ordering of the flow graph
recursively. Write a depth first traversal program and invoke it on the example
string

1->3->4->6->7->8->10

And print the large traversed node in that order.


PROGRAM:

#include<stdio.h>
#include<iostream.h>
#include<conio.h>
#include<ctype.h>
#include<string.h>
#include<stdlib.h>

class LiveVar
{
int no_node;
int DFN[20],dfn_n,dfst_n;
char mark[20];

struct dfs
{
int startN,endN;
}DFST[30];

struct FG
{
int paths;
int endNodes[10];
}flowGraph[20];

public:
void inputFlowGraph();
void printFlowGraph();
void findDFST();
void printDFST();
void search(int);
};

void LiveVar :: printDFST()


{
int i;

cout << "Depth First Spanning Tree:" << endl;


for(i=0;i<dfst_n;i++)
cout << DFST[i].startN << "->" << DFST[i].endN << endl;
cout << endl;
cout << "Depth First Ordering:" << endl;
for(i=1;i<=no_node;i++)
cout << DFN[i] << " ";
}

void LiveVar :: findDFST()


{
int m,i,j;

dfst_n = 0;
dfn_n = no_node;

for(i=1;i<=no_node;i++)
mark[i] = 'u';

search(1);
}

void LiveVar :: search(int node)


{
int i;

mark[node] = 'v';

for(i=0;i<flowGraph[node].paths;i++)
if( mark[flowGraph[node].endNodes[i]] == 'u')
{
DFST[dfst_n].startN = node;
DFST[dfst_n++].endN = flowGraph[node].endNodes[i];

search(flowGraph[node].endNodes[i]);
}

DFN[node] = dfn_n;
dfn_n = dfn_n - 1;
}

void LiveVar :: inputFlowGraph()


{
no_node=10;

flowGraph[1].paths=2;
flowGraph[1].endNodes[0]=2;
flowGraph[1].endNodes[1]=3;

flowGraph[2].paths=1;
flowGraph[2].endNodes[0]=3;

flowGraph[3].paths=1;
flowGraph[3].endNodes[0]=4;

flowGraph[4].paths=3;
flowGraph[4].endNodes[0]=5;
flowGraph[4].endNodes[1]=6;
flowGraph[4].endNodes[2]=3;

flowGraph[5].paths=1;
flowGraph[5].endNodes[0]=7;

flowGraph[6].paths=1;
flowGraph[6].endNodes[0]=7;

flowGraph[7].paths=2;
flowGraph[7].endNodes[0]=8;
flowGraph[7].endNodes[1]=4;

flowGraph[8].paths=3;
flowGraph[8].endNodes[0]=9;
flowGraph[8].endNodes[1]=10;
flowGraph[8].endNodes[2]=3;

flowGraph[9].paths=1;
flowGraph[9].endNodes[0]=1;

flowGraph[10].paths=1;
flowGraph[10].endNodes[0]=7;
}

void LiveVar :: printFlowGraph()


{
int i,j;

cout << "Node\tpaths" << endl;

for(i=1;i<=no_node;i++)
{
cout << i << "\t";
for(j=0;j<flowGraph[i].paths;j++)
cout << flowGraph[i].endNodes[j] << " ";
cout << endl;
}
}

void main()
{
LiveVar l;
clrscr();
l.inputFlowGraph();
l.printFlowGraph();
l.findDFST();
l.printDFST();
getch();
}

/*void Natural :: inputFlowGraph()


{
int i,j;

cout << "How many nodes:" << endl;


cin >> no_node;

for(i=0;i<no_node;i++)
{
cout << "For Node " << i+1 << ":" << endl;
cout << "How many paths to other nodes:";
cin >> flowGraph[i].paths;
for(j=0;j<flowGraph[i].paths;j++)
{
cout << "Path " << j+1 << " goes to the node:";
cin >> flowGraph[i].endNodes[j];
}
}
}*/

OUTPUT:

Node paths
1 23
2 3
3 4
4 563
5 7
6 7
7 84
8 9 10 3
9 1
10 7

Depth First Spanning Tree:


1->2
2->3
3->4
4->5
5->7
7->8
8->9
8->10
4->6

Depth First Ordering:


1 2 3 4 6 5 7 8 10 9
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-II)

PRACTICAL 10

Generate the assembly code for the intermediate representation obtains in the
triple.

Suppose the expression (a+b)*(c+d)


Triple is :
OP ARG1 ARG2
0 + a B
1 + c D
2 * (0) (1)
Then it’s assembly code is
MOV R0 a
ADD R0 b
MOV R1 c
ADD R1 d
MOV R2 R0
MUL R2 R1
PROGRAM:

// Assembler
#include<stdio.h>
#include<iostream.h>
#include<conio.h>
#include<ctype.h>
#include<string.h>
#include<stdlib.h>

class Grammer
{
struct qdrplr
{
char op;
char A1;
char A2;
int R;
} quadraple[10];

struct tripl
{
char op;
char A1;
char A2;
} triple[10];

struct assembly
{
char opr[10];
char A1[10];
char A2[10];
}assm[20];

int no_qdrpl;
int result;
int reg_count,reg;

public:
char *inputString;
int res;
char operators[20];
int no_op;
char variables[20];
int no_var;
Grammer(void);
void findQuadra();
int findOpenBrace(char*,int);
int findCloseBrace(char*,int);
char* subString(char*,int,int);
void printQuadra(void);
void findAssm(void);
};

void Grammer :: findAssm(void)


{
int i;

for(i=0;i<no_qdrpl;i++)
{
if(!(triple[i].A1 >= '0' && triple[i].A1 <= '9') && !(triple[i].A2 >= '0' &&
triple[i].A2 <= '9'))
{
sprintf(assm[reg_count].opr,"MOV");
sprintf(assm[reg_count].A1,"R%d",reg++);
sprintf(assm[reg_count++].A2,"%c",triple[i].A1);
}

if(triple[i].op=='+')
sprintf(assm[reg_count].opr,"ADD");
if(triple[i].op=='-')
sprintf(assm[reg_count].opr,"SUB");
if(triple[i].op=='*')
sprintf(assm[reg_count].opr,"MUL");
if(triple[i].op=='/')
sprintf(assm[reg_count].opr,"DIV");

if(!(triple[i].A2 >= '0' && triple[i].A2 <= '9'))


{
sprintf(assm[reg_count].A1,"R%d",reg-1);
sprintf(assm[reg_count].A2,"%c",triple[i].A2);
}
else
{
if(!(triple[i].A1 >= '0' && triple[i].A1 <= '9'))
{
sprintf(assm[reg_count].A1,"R%d",reg-1);
sprintf(assm[reg_count].A2,"%c",triple[i].A1);
}
else
{
sprintf(assm[reg_count].A1,"R%c",triple[i].A1);
sprintf(assm[reg_count].A2,"R%c",triple[i].A2);
}
}
reg_count++;
}
}
void Grammer :: printQuadra(void)
{
int i;
cout << endl << "Quadraple Table" << endl;
cout << "\tOP\tA1\tA2\tR" << endl;

for(i=0;i<no_qdrpl;i++)
{
cout << "E" << i << "\t" << quadraple[i].op << "\t" << quadraple[i].A1 << "\t"
<< quadraple[i].A2 << "\t" << quadraple[i].R << endl;
}

cout << endl << "Triple Table" << endl;


cout << "\tOP\tA1\tA2" << endl;

for(i=0;i<no_qdrpl;i++)
{
cout << i << "\t" << triple[i].op << "\t" << triple[i].A1 << "\t" << triple[i].A2
<< endl;
}

cout << endl << "Assembly Code" << endl;

for(i=0;i<reg_count;i++)
{
cout << "\t" << assm[i].opr << "\t" << assm[i].A1 << "\t" << assm[i].A2 <<
endl;
}

char* Grammer :: subString(char *str, int start, int end)


{
char* returnStr;
int k,l=0;

for(k=start;k<=end;k++)
returnStr[l++] = str[k];
returnStr[l] = '\0';
return returnStr;
}

void Grammer :: findQuadra()


{
int posOpenBrace,posCloseBrace,startExpr,endExpr;
int i,k,l;
char *subStr;

while(strlen(inputString) > 1)
{
startExpr=0;
endExpr=strlen(inputString);
posOpenBrace = findOpenBrace(inputString,0);
if(posOpenBrace != -1)
posCloseBrace = findCloseBrace(inputString,posOpenBrace);

if(posOpenBrace == -1) // no any bracket in string


{
for(k=0;k<strlen(inputString);k++)
{
if(inputString[k]=='*' || inputString[k]=='/' ||
inputString[k]=='%')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}

for(k=0;k<strlen(inputString);k++)
{
if(inputString[k]=='+' || inputString[k]=='-')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}
}

if(posCloseBrace == posOpenBrace+4) // omly one expr in brackets


{
startExpr=posOpenBrace;
endExpr=posCloseBrace;
goto getQuadra;
}

if(posOpenBrace != -1) // no any bracket in string


{
for(k=posOpenBrace;k<posCloseBrace;k++)
{
if(inputString[k]=='*' || inputString[k]=='/' ||
inputString[k]=='%')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}

for(k=posOpenBrace;k<posCloseBrace;k++)
{
if(inputString[k]=='+' || inputString[k]=='-')
{
startExpr=k-1;
endExpr=k+1;
goto getQuadra;
}
}
}

getQuadra:

if( inputString[startExpr]=='(' && inputString[endExpr]==')' ) // only one expr


in brackets
{
for(k=0;k<no_qdrpl;k++)
{
if( (int)quadraple[k].A1 == (int)inputString[startExpr+1] &&
(int)quadraple[k].op == (int)inputString[startExpr+2] && (int)quadraple[k].A2 ==
(int)inputString[startExpr+3])
{
res=k+2;
goto processStr;
//cout << endl << "true";
}
}

quadraple[no_qdrpl].A1 = inputString[startExpr+1];
quadraple[no_qdrpl].op = inputString[startExpr+2];
quadraple[no_qdrpl].A2 = inputString[startExpr+3];
quadraple[no_qdrpl].R = result++;

if(inputString[startExpr+1] >= '0' && inputString[startExpr+1] <= '9')


triple[no_qdrpl].A1 = inputString[startExpr+1]-1;
else
triple[no_qdrpl].A1 = inputString[startExpr+1];

triple[no_qdrpl].op = inputString[startExpr+2];

if(inputString[startExpr+3] >= '0' && inputString[startExpr+3] <= '9')


triple[no_qdrpl].A2 = inputString[startExpr+3]-1;
else
triple[no_qdrpl].A2 = inputString[startExpr+3];

res=result;
no_qdrpl++;
}
else
{
for(k=0;k<no_qdrpl;k++)
{
if( (int)quadraple[k].A1 == (int)inputString[startExpr] &&
(int)quadraple[k].op == (int)inputString[startExpr+1] && (int)quadraple[k].A2 ==
(int)inputString[startExpr+2])
{
res=k+2;
goto processStr;
}
}

quadraple[no_qdrpl].A1 = inputString[startExpr];
quadraple[no_qdrpl].op = inputString[startExpr+1];
quadraple[no_qdrpl].A2 = inputString[startExpr+2];
quadraple[no_qdrpl].R = result++;

if(inputString[startExpr] >= '0' && inputString[startExpr] <= '9')


triple[no_qdrpl].A1 = inputString[startExpr]-1;
else
triple[no_qdrpl].A1 = inputString[startExpr];

triple[no_qdrpl].op = inputString[startExpr+1];

if(inputString[startExpr+2] >= '0' && inputString[startExpr+2] <= '9')


triple[no_qdrpl].A2 = inputString[startExpr+2]-1;
else
triple[no_qdrpl].A2 = inputString[startExpr+2];

res=result;
no_qdrpl++;
}

processStr:
strcpy(subStr,"");
l=0;
k=0;
while(inputString[k] != '\0')
{
if(startExpr == k)
{
subStr[l] = 48+res-1;
k = endExpr+1;
}
else
{
subStr[l] = inputString[k];
k++;
}
l++;
}
subStr[l] = '\0';
strcpy(inputString,subStr);
}
}

int Grammer :: findOpenBrace(char *str,int startPos)


{
int k,currentPos=-1;

for(k=startPos;k<strlen(str);k++)
{
if(str[k] == '(')
currentPos=k;
if(str[k] == ')')
break;
}

return currentPos;
}

int Grammer :: findCloseBrace(char *str,int startPos)


{
int k;

for(k=startPos;k<strlen(str);k++)
if(str[k] == ')')
return k;
return -1;
}

Grammer :: Grammer(void)
{
int i,j;
clrscr();

no_op=0;
no_var=0;
no_qdrpl=0;
reg_count=0;
reg=0;
result=1;
cout << "Enter the String:";
gets(inputString);
//inputString="(a+b)*(c+d)";

for(i=0;i<strlen(inputString);i++)
{
if(inputString[i] != ' ')
{
if( ((int)inputString[i] >= 65 && (int)inputString[i] <= 90) ||
((int)inputString[i] >= 97 && (int)inputString[i] <= 122) )
{
for(j=0;j<no_var;j++)
if(inputString[i] == variables[j])
goto nextVar;
variables[no_var++] = inputString[i];
nextVar:
}
else
if(inputString[i] == '+' || inputString[i] == '-' || inputString[i] ==
'*' || inputString[i] == '/' || inputString[i] == '%' || inputString[i] == '(' || inputString[i] == ')')
{
if(inputString[i] != '(' && inputString[i] != ')')
{
for(j=0;j<no_op;j++)
if(inputString[i] == operators[j])
goto nextOp;
operators[no_op++] = inputString[i];
nextOp:
}
}
else
{
cout << endl << inputString[i] << " is encoutered in the
string as invalid character, Thus the string is invalid.";
getch();
exit(0);
}
}
}

cout << endl << "Variables are as Follows:" << endl;


for(i=0;i<no_var;i++)
cout << variables[i] << " ";

cout << endl << "Operators are as Follows:" << endl;


for(i=0;i<no_op;i++)
cout << operators[i] << " ";
}

int main(void)
{
Grammer g;
//int result;
//G1.PrintGrammer();
//dg.FindFirstFollow();
g.findQuadra();
g.findAssm();
cout << endl;
g.printQuadra();
getch();
return 0;
}

OUTPUT:

Enter String:a*b+c*d

Variables are as Follows:


abcd
Operators are as Follows:
*+

Quadraple Table
OP A1 A2 R
E0 * a b 1
E1 * c d 2
E2 + 1 2 3

Triple Table
OP A1 A2
0 * a b
1 * c d
2 + 0 1

Assembly Code
MOV R0 a
MUL R0 b
MOV R1 c
MUL R1 d
ADD R0 R1
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-II)

PRACTICAL 11

Postfix to Infix Conversion


Write a program to obtain an operation in postfix form and convert it to infix
form using a suitable algorithm

Postfix expression : a b c * +

Infix form : a + b * c
PROGRAM:

#include<stdio.h>

#define MAX 100

void pop (char*);


void push(char*);

char stack[MAX][MAX];
int top = -1;

void main()
{
char s[MAX], str1[MAX], str2[MAX], str[MAX];
char s1[2],temp[2];
int i=0;
clrscr( ) ;

printf("\Enter the postfix expression: ");

gets(s);

while (s[i]!='\0')
{
/*skip whitespace, if any*/
if(s[i] == ' ')
i++;

if (s[i] == '%' || s[i] == '*'|| s[i] == '-' || s[i] == '+' || s[i] == '/')
{
pop(str1);
pop(str2);

temp[0] ='(';
temp[1] ='\0';

strcpy(str, temp);
strcat(str, str2);

temp[0] = s[i];

temp[1] = '\0';

strcat(str,temp);

strcat(str, str1);

temp[0] =')';
temp[1] ='\0';

strcat(str,temp);

push(str);
}
else
{
temp[0]=s[i];

temp[1]='\0';

strcpy(s1, temp);

push(s1);

}
i++;
}
printf("\n%s", stack[0]);
}

void pop(char *a1)


{
strcpy(a1,stack[top]);
top--;
}

void push (char*str)


{
if(top == MAX - 1)
printf("\nstack is full");
else
{
top++;
strcpy(stack[top], str);
}
}
OUTPUT:

Enter infix expression: ab+c*


((a+b)*c)

Enter infix expression: abc*+


(a+(b*c))

Enter infix expression: ab+cd+*


((a+b)*(c+d))

Enter infix expression: ab-cd+e-f*+


((a-b)+((c+d)-e)*f)
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-II)

PRACTICAL 12

Infix to Postfix Conversion

Write a program to obtain an operation in infix form and convert it to postfix


form using a suitable algorithm

Infix expression: a + b * c

Postfix form : a b c * +
PROGRAM:

#include<stdio.h>
#include<stdlib.h>

#define MAXCOLS 80
#define TRUE 1
#define FALSE 0

void postfix(char*,char*);
int isoperand(char);
void popandtest(struct stack*,char*,int*);
int prcd(char,char);
void push(struct stack*,char);
char pop(struct stack*);

struct stack
{
int top;
char items[MAXCOLS];
};

void main()
{
char infix[MAXCOLS];
char postr[MAXCOLS];
int pos=0;

clrscr();
printf("Enter infix expression:");
while((infix[pos++] = getchar()) != '\n');
infix[--pos]='\0';
postfix(infix,postr);
printf("%s\n",postr);
getch();
}

void postfix(char *infix,char *postr)


{
int position,und;
int outpos=0;
char topsymb='+';
char symb;
struct stack opstk;
opstk.top=-1;

for(position=0;(symb=infix[position])!='\0';position++)
{
if(!isoperand(symb))
postr[outpos++] = symb;
else
{
popandtest(&opstk,&topsymb,&und);
while(!und && prcd(topsymb,symb))
{
postr[outpos++] = topsymb;
popandtest(&opstk,&topsymb,&und);
}

if(!und)
push(&opstk,topsymb);

if(und || symb!=')')
push(&opstk,symb);
else
topsymb = pop(&opstk);
}
}

while(!empty(&opstk))
postr[outpos++] = pop(&opstk);
postr[outpos] = '\0';
}

int isoperand(char symb)


{
return (symb=='(' || symb==')' || symb=='*' || symb=='/' || symb=='+' || symb=='-' ||
symb=='%');
}

void popandtest(struct stack *ps,char *px,int *pund)


{
if(empty(ps))
{
*pund=TRUE;
return;
}
*pund = FALSE;
*px = ps->items[ps->top--];
return;
}

int prcd(char s1,char s2)


{
if((s1=='*' || s1=='/' || s1=='%') && (s2=='+' || s2=='-'))
return TRUE;

if((s1=='+'|| s1=='-') && (s2=='*' || s2=='/' || s2=='%'))


return FALSE;
if( s1=='(' && (s2=='*' || s2=='/' || s2=='+' || s2=='-' || s2=='%' || s2==')') )
return FALSE;

if( (s1=='(' || s1=='*' || s1=='/' || s1=='+' || s1=='-' || s1=='%') && s1!=')' && s2=='(')
return FALSE;

if( (s1==')' || s1=='*' || s1=='/' || s1=='+' || s1=='-' || s1=='%') && s1!='(' && s2==')')
return TRUE;
}

void push(struct stack* ps,char x)


{
ps->items[++(ps->top)] = x;
return;
}

char pop(struct stack *ps)


{
if(empty(ps))
{
printf("%","stack underflow");
exit(1);
}
return(ps->items[ps->top--]);
}

int empty(struct stack *ps)


{
if(ps->top == -1)
return TRUE;
else
return FALSE;
}
OUTPUT:

Enter infix expression:(a+b)*c


ab+c*

Enter infix expression:a+b*c


abc*+

Enter infix expression:(a+b)*(c+d)


ab+cd+*

Enter infix expression:((a-b)+((c+d)-e)*f)


ab-cd+e-f*+
Roll No. – 22

NAAC Accreditation “A” Grade


Deccan Education Society’s
Kirti M. Doongursee College, Dadar, Mumbai-28
Dept. of Computer Science & I.T.
M.Sc. (Part-I) 2006 – 07

Compiler Construction (Section-II)

PRACTICAL 13

Input a file. Search for the token viz. variable, operator symbols, & constants &
maintain the list of such tokens separately under separate classes.

Consider, read the file contain the addition of two numbers program then write
a program to identify the variable, constant & operator in your program &
display this variable, constant & operator on console.
Main()
{
int a,c;
c=a+100;
printf(“Sum=%d”);
}
Then the o/p is :
Variable => a, c
Constants => 100
Operator => +, =
PROGRAM:

#include<stdio.h>
#include<iostream.h>
#include<conio.h>
#include<ctype.h>
#include<string.h>
#include<stdlib.h>

class Grammer
{
public:
Grammer(void);
char *str;
char words[30][30];
int wordLen[100];
int noOfWords;
void findWords(void);
char vars[50];
char operators[50];
int constants[50];
int no_vars,no_op,no_const;
};

Grammer :: Grammer(void)
{
FILE* f1;
char c;
char *tmp;
int i=0,j,wordFound=0,k;
no_vars=0;
no_op=0;
no_const=0;
int tmpNum=0;

clrscr();
f1 = fopen("d:\\msc\\compiler\\try.txt","r");

while((c=getc(f1)) != EOF)
str[i++] = c;
str[i]='\0';

noOfWords=0;
j=0;
i=strlen(str);
for(i=0;i<strlen(str);i++)
{
if(str[i]==' ' || str[i]==';' || str[i]=='\n' || str[i]=='\t' || str[i]==',' || str[i]=='{' || str[i]=='}')
{
if(wordFound==1)
{
wordLen[noOfWords]=j;
noOfWords++;
j=0;
wordFound=0;
}
}
else
{
words[noOfWords][j++]=str[i];
if(str[i]=='+' || str[i]=='-' || str[i]=='*' || str[i]=='/' || str[i]=='%' || str[i]=='=')
{
wordLen[noOfWords]=j;
noOfWords++;
j=0;
wordFound=0;
}
else
wordFound=1;
}
}

for(i=0;i<noOfWords;i++)
{
if(strcmp(words[i],"int")==0)
{
cout << endl;
wordLen[i]=0;
words[i][0]='\0';
goto nextWord;
}
for(j=0;j<wordLen[i];j++)
{
if(words[i][j]=='(' || words[i][j]==')' || words[i][j]=='"')
{
wordLen[i]=0;
words[i][0]='\0';
goto nextWord;
}
}

for(j=0;j<wordLen[i];j++)
{
if(!((int)words[i][j]>=48 && (int)words[i][j]<=57))
{
goto nextWord;
}
}
constants[no_const++]=atoi(words[i]);
wordLen[i]=0;
words[i][0]='\0';
nextWord:
}

for(i=0;i<noOfWords;i++)

{
for(j=0;j<wordLen[i];j++)
{
if(words[i][j]=='+' || words[i][j]=='-' || words[i][j]=='*' || words[i][j]=='/' ||
words[i][j]=='=' || words[i][j]=='%')
{
for(k=0;k<no_op;k++)
if(operators[k]==words[i][j])
goto nextVar;
operators[no_op++]=words[i][j];
nextVar:
}
else
{
for(k=0;k<no_vars;k++)
if(vars[k]==words[i][j])
goto nextOp;
vars[no_vars++]=words[i][j];
nextOp:
}
}
}

cout << "Variables:" << endl;


for(i=0;i<no_vars;i++)
cout << vars[i] << ",";

cout << endl << "Operators:" << endl;


for(i=0;i<no_op;i++)
cout << operators[i] << ",";

cout << endl << "Constants:" << endl;


for(i=0;i<no_const;i++)
cout << constants[i] << ",";
}

void main()
{
Grammer g;
getch();
}
FILE INPUT:

Try.txt

main()
{
int a,c;
c=a+100;
printf("%d",c);
}

OUTPUT:

Variables:
a,c

Operators:
=,+

Constants:
100

You might also like