반응형
수식 트리
# 이진트리의 활용법 중 하나인 수식트리
# 문자열로 수식을 입력받아 그 결과를 리턴해준다.
# 큐와 스택은 앞에서 만든걸 활용했다.
C++로 구현한 수식트리
#pragma once #include "Queue_list.h" #include "stack_list.h" #include <iostream> #include <tchar.h> #if defined(UNICODE) || defined(_UNICODE) #define tcout std::wcout #define tcin std::wcin #else #define tcout std::cout #define tcin std::cin #endif struct node { TCHAR data; node* left; node* right; }; node* MakeNode(TCHAR data) { node* nn = new node; nn->data = data; nn->left = nullptr; nn->right = nullptr; return nn; } class ExpressionTree { TCHAR infixStr[256]; QueueList<TCHAR> PostfixQueue; StackList<TCHAR> OperatorStack; StackList<node*> NodeStack; private: int Prioty(TCHAR op1); void InToPost(); node* constructTree(node* root, node* left, node* right); void MakeEXPTree(); public: node * ExpTree; public: void InputFormula(const TCHAR* str); void inorder(node* n); int calculate(node* n); public: ExpressionTree(); virtual ~ExpressionTree(); }; ExpressionTree::ExpressionTree() { } void ExpressionTree::InputFormula(const TCHAR* str) { _tcscpy_s(infixStr, str); InToPost(); MakeEXPTree(); } int ExpressionTree::Prioty(TCHAR op) { if (op == '+' || op == '-') { return 1; } if (op == '*' || op == '/') { return 2; } } void ExpressionTree::InToPost() { int iStrlen = _tcslen(infixStr) + 1; for (int i = 0; i < iStrlen; i++) { if (isdigit(infixStr[i])) { PostfixQueue.Add(infixStr[i]); } else { if (OperatorStack.Count() == 0) { OperatorStack.Push(infixStr[i]); } else { if (Prioty(OperatorStack.Peek()) < Prioty(infixStr[i])) { OperatorStack.Push(infixStr[i]); } else { PostfixQueue.Add(OperatorStack.Pop()); i--; continue; } } } } } node* ExpressionTree::constructTree(node* root, node* left, node* right) { root->data = root->data; root->left = left; root->right = right; return root; } void ExpressionTree::MakeEXPTree() { int count = PostfixQueue.Count(); for (int i = 0; i < count; i++) { char oper = PostfixQueue.Peek(); PostfixQueue.Remove(); NodeStack.Push(MakeNode(oper)); if (oper == '+' || oper == '-' || oper == '*' || oper == '/') { node* root = NodeStack.Pop(); node* right = NodeStack.Pop(); node* left = NodeStack.Pop(); NodeStack.Push(constructTree(root, left, right)); } } ExpTree = NodeStack.Peek(); } void ExpressionTree::inorder(node* n) { if (n != nullptr) { inorder(n->left); std::cout << n->data; inorder(n->right); } } int ExpressionTree::calculate(node* n) { int op1, op2; if (n->left == nullptr && n->right == nullptr) { return n->data - 48; } op1 = calculate(n->left); op2 = calculate(n->right); switch (n->data) { case '+': {return op1 + op2; } break; case '-': {return op1 - op2; } break; case '*': {return op1 * op2; } break; case '/': {return op1 / op2; } break; } return 0; } ExpressionTree::~ExpressionTree() { }
main예제
#include "ExpressionTree.h" int main() { ExpressionTree a; a.InputFormula("3+2*5"); a.inorder(a.ExpTree); std::cout << '=' << a.calculate(a.ExpTree); }
반응형