簡體   English   中英

使用堆棧的 C++ 后綴表達式評估。 我認為我沒有正確轉換數據

[英]C++ Postfix expression evaluation using stacks. I dont think I'm converting the data correctly

我目前正在嘗試讓這個后綴表達式 eval 起作用,但我相信在int EvaluatePostfix函數中我錯誤地使用了stackPtr->peek()因為每當我嘗試獲取最高值並將其減去“0”(不是顯示在代碼中,mb) 將其轉換為 int 它說它是一個“std::basic_string-char-”所以它不能用char類型進行減法。

后綴.cpp:

#include <iostream>
#include <string>
#include "ArrayStack.h"


bool IsNumericDigit(char C)
{
    if(C >= '0' && C <= '9') return true;
    return false;
}

// Function to verify whether a character is operator symbol or not.
bool IsOperator(char C)
{
    if(C == '+' || C == '-' || C == '*' || C == '/')
        return true;

    return false;
}

// Function to perform an operation and return output.
int PerformOperation(char operation, int operand1, int operand2)
{
    if(operation == '+') return operand1 +operand2;
    else if(operation == '-') return operand1 - operand2;
    else if(operation == '*') return operand1 * operand2;
    else if(operation == '/') return operand1 / operand2;

    else std::cout<<"Unexpected Error \n";
    return -1;
}

int EvaluatePostfix(std::string expression, StackInterface<std::string>* stackPtr)
{
    

    for(int i = 0;i< expression.length();i++)
    {

        // Scanning each character from left.
        // If character is a delimiter, move on.
        if(expression[i] == ' ' || expression[i] == ',') continue;

            // If character is operator, pop two elements from stack, perform operation and push the result back.
        else if(IsOperator(expression[i]))
        {
            
            // Pop two operands.
            int operand2 = stackPtr->peek(); 
            stackPtr->pop();
            int operand1 = stackPtr->peek(); 
            stackPtr->pop();
            
            //operand1 and operand2 are reversed in case of Prefix Expression
            
            // Perform operation
            int result = PerformOperation(expression[i], operand1, operand2);
            //Push back result of operation on stack.
            stackPtr->push(result);
        }
        else if(IsNumericDigit(expression[i]))
        {
            // Extract the numeric operand from the string
            // Keep incrementing i as long as you are getting a numeric digit.
            int operand = 0;
            while(i<expression.length() && IsNumericDigit(expression[i]))
            {
                // For a number with more than one digits, as we are scanning from left to right.
                // Everytime , we get a digit towards right, we can multiply current total in operand by 10
                // and add the new digit.
                operand = (operand*10) + (expression[i] - '0');
                std::cout << operand << std::endl;
                i++;
            }
            // Finally, you will come out of while loop with i set to a non-numeric character or end of string
            // decrement i because it will be incremented in increment section of loop once again.
            // We do not want to skip the non-numeric character by incrementing i twice.
            i--;

            // Push operand on stack.
            stackPtr->push(operand);
        }
    }
    // If expression is in correct format, Stack will finally have one element. This will be the output.
    return stackPtr->top();
}

int main(){
    StackInterface<std::string>* stackPtr = new ArrayStack<std::string>();
    std::string expression;
    std::cout<<"Enter Postfix Expression \n";
    std::getline(std::cin,expression);
    EvaluatePostfix(expression, stackPtr)
    std::cout << stackPtr->push(expression);
    
}

ArrayStack.h:

#ifndef ARRAY_STACK_EXCEPTIONS
#define ARRAY_STACK_EXCEPTIONS

#include "StackInterface.h"
#include "PrecondViolatedExcep.h"

const int MAX_STACK = 1000;

template<class ItemType>
class ArrayStack : public StackInterface<ItemType>
{
private:
    ItemType items[MAX_STACK]; // Array of stack items
    int      top;              // Index to top of stack
    
public:
     ArrayStack();
     bool isEmpty() const;
     bool push(const ItemType& newEntry);
     bool pop();
     ItemType peek() const; 
}; // end ArrayStack


template<class ItemType>
ArrayStack<ItemType>::ArrayStack() : top(-1)
{
}  // end default constructor

// Copy constructor and destructor are supplied by the compiler

template<class ItemType>
bool ArrayStack<ItemType>::isEmpty() const
{
    return top < 0;
}  // end isEmpty

template<class ItemType>
bool ArrayStack<ItemType>::push(const ItemType& newEntry)
{
    bool result = false;
    if (top < MAX_STACK - 1)
    {
        // Stack has room for another item
        top++;
        items[top] = newEntry;
        result = true;
    }  // end if
    
    return result;
}  // end push


template<class ItemType>
bool ArrayStack<ItemType>::pop()
{
    bool result = false;
    if (!isEmpty())
    {
        result = true;
        top--;
    }  // end if
    
    return result;
}  // end pop


template<class ItemType>
ItemType ArrayStack<ItemType>::peek() const
{
    // Enforce precondition
    if (isEmpty())
        throw PrecondViolatedExcep("peek() called with empty stack");
        
        // Stack is not empty; return top
        return items[top];
}  // end peek

編輯:將stackPtr->peek()減去 '0' 時得到的錯誤是“與 'operator-' 不匹配(操作數類型為 'std::basic_stringchar' 和 char'”

謝謝!

這里的問題是您可以互換使用std::stringcharint ,而它們不是。

請注意,堆棧的數據類型是string ,並且沒有從string更改為int或將string更改為char默認方法。

根據您的描述,您試圖從string獲取第一個char ,您可能會調用它:

c = stackPtr->peek()[0];

或者

c = stackPtr->peek().front();

string to int會調用std::stoi(stackPtr->peek()) ,但不確定你是否想要它,因為你自己實現它。

所以你可能想把這部分提取為一個單獨的函數:

while(i<expression.length() && IsNumericDigit(expression[i]))
{    
    operand = (operand*10) + (expression[i] - '0');
    std::cout << operand << std::endl;
    i++;
}

因此,當您從堆棧中獲取string時,您可以輕松地重用它。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM