2016-05-05 100 views
0

我正在處理的程序是下推自動機,它只接受^ nb^n的輸入:$ ab,$ aabb,$ aaabbb等。關於它的一切似乎工作,除了主while循環的4次迭代後得到分段錯誤的事實。我認爲這與我在每個循環中將堆棧複製到另一個堆棧的事實有關,但我不明白爲什麼它不會每次迭代都會出錯。任何幫助是極大的讚賞!將堆棧複製到沒有分割的堆棧錯誤

#include <iostream> 
#include <stack> 
#include <string> 

using namespace std; 

int main() 
{ 
    cout << "Enter an expression: "; 
    string expression; 
    getline(cin, expression); 

    stack<char> expressionStack; 
    stack<char> unreadStack; 
    stack<char> expressionStackPOP; 
    stack<char> unreadStackPOP; 
    char expressionOutput; 
    char readInput; 
    char transitionState = 'p'; 
    int step=0; 
    int counter; 
    int trule = 0; 
    int rrule = 0; 
    char expressionO; 
    char unreadO; 

    //Enter expression into Stack<char> unreadInput 
    for(unsigned int i = 0; i<expression.length(); i++) 
    { 
     unreadStack.push(expression[i] 
      ); 
    } 
    counter = expression.length(); 
    cout << "Got passed putting the expression in unreadStack" << endl; 
    cout <<"Step"<< "\tState" << "\tUnread Input" << "\t\tStack" <<"\t\tΔ Rule used " << "\tR rule used "<< endl; 
    while(!unreadStack.empty()) 
    { 
     switch(transitionState) 
     { 
     case 'p': 
      expressionStack.push('S'); 
      transitionState = 'q'; 
      trule = 1; 
      //cout << "Changed state to P and pushed S into stack" << endl; 
      break; 
     case 'q': 
      if(unreadStack.top() == 'a' && transitionState=='q') 
      { 
       readInput = unreadStack.top(); 
       unreadStack.pop(); 
       transitionState = 'a'; 
       trule = 2; 
       //cout << "Changed state to qa and popped a from unread stack" << endl; 
      } 
      if(unreadStack.top() == 'b' && transitionState=='q') 
      { 
       readInput = unreadStack.top(); 
       unreadStack.pop(); 
       transitionState = 'b'; 
       trule = 3; 
       //cout << "Changed state to qb and popped b from unread stack"<<endl; 
      } 
      if(unreadStack.top() == '$' && transitionState=='q') 
      { 
       readInput = unreadStack.top(); 
       unreadStack.pop(); 
       transitionState = '$'; 
       trule = 4; 
       //cout << "This is the end" << endl; 
      } 
      break; 
     case 'a': 
      //cout << "in case a" << endl; 
      if(readInput=='a' && transitionState=='a') 
      { 
       expressionStack.pop(); 
       transitionState='q'; 
       trule = 5; 
       //cout << "Changed state to q and popped a from stack" << endl; 
      } 
      if(readInput=='S' && transitionState=='a') 
      { 
       expressionStack.pop(); 
       expressionStack.push('b'); 
       expressionStack.push('S'); 
       expressionStack.push('a'); 
       transitionState='q'; 
       trule = 6; 
       //cout << "Changed state to q and popped S from stack and pushed aSb into stack" << endl; 
      } 
      break; 
     case 'b': 
      if(readInput=='b' && transitionState=='b') 
      { 
       expressionStack.pop(); 
       transitionState='q'; 
       trule = 7; 
       //cout << "Changed state to q and popped b from stack" << endl; 
      } 
      if(readInput=='S' && transitionState=='b') 
      { 
       expressionStack.pop(); 
       transitionState='b'; 
       trule = 8; 
       //cout << "Changed state to qb and popped S from stack" << endl; 
      } 
      break; 
     case '$': 
      cout<<"test"<<endl; 
      break; 
      trule = 9; 
     } 

     //Output RIGHT HERE THIS IS THE SPOT----------------------------------------------------- 
     expressionStackPOP = expressionStack; 
     unreadStackPOP = unreadStack; 
     //-------------------------------------------------------------- 

     if (step<=9) 
      cout<<" "; 
     cout <<step<<"\t"<<transitionState<<"\t"; 
     while(!unreadStackPOP.empty())//copy unreadStackPOP stack to string 
     { 
      cout<<unreadO; 
      unreadO = unreadStackPOP.top(); 
      unreadStackPOP.pop(); 
     } 
     cout<<"\t\t\t"; 
     while(!expressionStackPOP.empty())//copy expressionStackPOP stack to string 
     { 
      cout<<expressionO; 
      expressionO = expressionStackPOP.top(); 
      expressionStackPOP.pop(); 
     } 
     cout<<"\t\t"<<trule<<"\t\t"<<rrule<<endl; 
     step++; 
    } 
} 
+0

似乎至少偶爾檢查一下'expressionStack.empty()'會在這段代碼的重要部分中證明有用。 – WhozCraig

回答

1

此代碼:

 if(unreadStack.top() == 'a' && transitionState=='q') 
     { 
      readInput = unreadStack.top(); 
      unreadStack.pop(); 
      transitionState = 'a'; 
      trule = 2; 
      //cout << "Changed state to qa and popped a from unread stack" << endl; 
     } 
     if(unreadStack.top() == 'b' && transitionState=='q') 
     { 

考慮一下,如果在這段代碼的開始,unreadStack只包含一個'a'會發生什麼。

第二個if聲明試圖做什麼?

+0

對不起,我忘了提及,自動機只接受^ nb^n的輸入:$ ab,$ aabb,$ aaabbb等。 – BillyB