Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- //#pragma once
- #include <iostream>
- #include <string>
- #include <cmath>
- #include <cstdio>
- #include <cstdlib>
- using namespace std;
- ///////////////////
- int potega(int liczba , int potega )
- {
- int wynik = liczba;
- for(int i=1;i<potega;i++)
- {
- wynik = wynik * liczba;
- }
- return wynik;
- }
- ///////////////////
- //////
- //////
- //////
- class Stos
- {
- private:
- int *tab; // dynamiczna tablica do przechowywania danych
- long size; // ilosc elementow, ktore moze pomiescic stos
- long last; // numer elementu na gorze stosu
- long Numbers; // liczba elementow na stosie
- public:
- Stos(void);
- Stos(long lSize);
- void Push(int elem);
- int Pop();
- const int& Top();
- void GrowStack();
- long GetNumbers();
- public:
- ~Stos(void);
- };
- class Calc
- {
- private:
- string line;
- string result;
- string operation;
- string oper;
- int ilLiczb;
- int ilZnakow;
- string ex;
- public:
- Calc();
- int RPN(string operation);
- int Result(string operation);
- ~Calc(void);
- };
- //////////////////////////////////
- Stos::Stos(void)
- {
- // konstruktor domyslny
- last = 0; // pusty stos
- size = 20; // ilosc elementow, ktore stos moze pomiescic
- Numbers = 0;
- tab = new int[size]; // przydzielamy dynamicznie pamiec
- if(tab == NULL) // blad przy alokacji pamieci
- {
- throw "Blad alokcacji pamieci!"; // wyjatek
- }
- }
- Stos::Stos(long lSize)
- {
- // konstruktor parametryczny
- last = 0; // pusty stos
- size = lSize; // ilosc elementow, ktore stos moze pomiescic
- Numbers = 0;
- tab = new int[size]; // przydzielamy dynamicznie pamiec
- if(tab == NULL) // blad przy alokacji pamieci
- {
- throw "Blad alokcacji pamieci!"; // wyjatek
- }
- }
- void Stos::Push(int elem)
- {
- if(last < size) // sprawdzamy czy na stosie jest miejsce
- {
- tab[last ++] = elem; // umieszczamy element na gorze stosu
- Numbers ++;
- }
- else
- {
- GrowStack(); // powiekszamy stos
- }
- }
- int Stos::Pop()
- {
- if(last >= 0) // sprawdzamy czy na stosie jest jakis element
- {
- Numbers --;
- return tab[--last]; // zdejmujemy element ze stosu
- }
- }
- const int& Stos::Top()
- {
- return tab[last - 1]; // pokazuje element, ktory jest na szczycie stosu
- }
- void Stos::GrowStack()
- {
- int *newTab = new int[size + 10]; // powiekszamy nowa tablice o 10 elementow
- for(int i=0; i < size; i++)
- newTab[i] = tab[i]; // przekopiowujemy zawartosc starej tablicy do nowej
- delete []tab; // kasujemy stara tablice
- tab = newTab; // przypisujemy nowa tablice jako "stara"
- size += 10; // zmieniamy wielkosc tablicy na aktualna
- }
- long Stos::GetNumbers()
- {
- return Numbers;
- }
- Stos::~Stos(void)
- {
- delete []tab; // zwalniamy zajeta pamiec
- }
- ////////////////////////
- Calc::Calc()
- {
- result = "";
- operation = "";
- ilLiczb = 0;
- ilZnakow = 0;
- }
- int Calc::RPN(string operation)
- {
- Stos *stack = new Stos;
- result = "";
- ilLiczb=0;
- ilZnakow=0;
- for(int i=0; i < operation.size(); i++)
- {
- if ((operation[i] >= '0' && operation[i] <= '9')) { // sprawdzamy czy pierwszy element jest liczba
- result += operation[i];
- if (!(operation[i+1] >= '0' && operation[i+1] <= '9')) { // sprawdzamy czy kolejny element nie jest liczba i dodajemy spacje
- result += " ";
- ilLiczb++;
- }
- }
- else if (operation[i] == '*' || operation[i] == '/' || operation[i] == '-'|| operation[i] == '+' || operation[i] == '^')
- {
- if(stack->Top()==NULL)
- {
- stack->Push((int)operation[i]);
- ilZnakow++;
- }
- else
- {
- char x = operation[i];
- char y = stack->Pop();
- if((y == '*' || y == '/') || ((y == '+' || y == '-') && x != '*' && x != '/'))
- {
- result += y;
- result += " ";
- while(stack->GetNumbers()>0)
- {
- result += stack->Pop();
- result += " ";
- }
- stack->Push(x);
- }
- else
- {
- stack->Push(y);
- stack->Push(x);
- }
- ilZnakow++;
- }
- }
- else
- {
- if(operation[i] != ' ')
- {
- ex = "Wystapily niepoprane znaki w wyrazeniu (np. litery)!";
- throw ex;
- }
- }
- }
- while(stack->GetNumbers()>0)
- {
- result += stack->Pop();
- result += " ";
- }
- //cout << ilLiczb << "test" << ilZnakow;
- if(ilLiczb != ilZnakow + 1)
- {
- ex = "Niepoprawne wyrazenie (ilosc znakow musi byc o jeden mniejsza od ilosci liczb) ";
- throw ex;
- }
- //cout << result << endl;
- return Result(result);
- }
- int Calc::Result(string operation)
- {
- Stos *stack2 = new Stos;
- stack2->Pop();
- int op;
- int op2;
- string res;
- //cout << "t" << operation.size();
- for(int i=0; i < operation.size(); i++)
- {
- res = "";
- int k = 200;
- //cout << "i" << i;
- //cout << stack2->Top() << endl;
- switch (operation[i])
- {
- case '0':
- case '1':
- case '2':
- case '3':
- case '4':
- case '5':
- case '6':
- case '7':
- case '8':
- case '9':
- res = operation[i];
- stack2->Push(atoi(res.c_str()));
- break;
- case '*':
- op2 = stack2->Pop() * stack2->Pop();
- stack2->Push(op2);
- break;
- case '/':
- op2 = stack2->Pop();
- if (op2 != 0)
- {
- op = stack2->Pop() / op2;
- stack2->Push(op);
- }
- else {
- cout << "Blad dzielenia przez zero!" << endl;
- }
- break;
- case '+':
- op2 = stack2->Pop() + stack2->Pop();
- stack2->Push(op2);
- break;
- case '^':
- op2 = potega(stack2->Pop(), stack2->Pop());
- stack2->Push(op2);
- break;
- case ' ':
- break;
- case '-':
- op2 = stack2->Pop();
- op = stack2->Pop() - op2;
- stack2->Push(op);
- break;
- default:
- cout << "Blad - nieznany znak!" << endl;
- }
- }
- //cout << "Wynik wyrazenia: " <<endl;
- //cout << stack2->Pop() << endl;
- return stack2->Pop();
- }
- Calc::~Calc(void)
- {
- }
- //////
- ////// te wszystkie klasy można by walnac w jakims includzie, ale skoro jeden plik ma byc.... xd
- //////
- void parser();
- int error();
- bool sprawdz_nawiasy();
- // zmienne
- string input;
- // -------
- int main()
- {
- int n;
- cin >> n;
- for (int i=0; i<n; i++)
- {
- parser();
- }
- }
- int error()
- {
- cout << "error";
- // exit(EXIT_FAILURE);
- }
- void parser()
- {
- Calc Wynik;
- string x,y;
- const char* pi = "3.141592653589";
- const char* e = "2.7182818285";
- cin >> input >> x >> y;
- //wstaw do stringa odpowiednie liczby pod x i y oraz pi i e
- input.replace(input.find('x'),1,x);
- input.replace(input.find('y'),1,y);
- // input.replace(input.find('pi'),1,pi);
- // input.replace(input.find('e'),1,e);
- //---------------------------------------------
- if (sprawdz_nawiasy()==false)
- {
- error();
- }
- else
- {
- ///
- string func,wyrazenie,zamiana;
- for (int i=0; i<input.length(); i++)
- {
- if (input[i] == '(' && !isdigit(input[i-1]))
- {
- for (int j=5; j>0; j--)
- {
- if (!isdigit(input[i-j]))
- {
- func += input[i-j];
- }
- }
- int k=0;
- while (input[i+k]==')')
- {
- wyrazenie += input[i+k];
- k++;
- }
- zamiana += func;
- zamiana += "(";
- zamiana += wyrazenie;
- zamiana += ")";
- int q;
- q = Wynik.RPN(wyrazenie);
- if (func == "abs")
- {
- input.replace(input.find(zamiana),1,abs(q));
- }
- // pozostalwe funkcje sie wklei jak pierwsza bedzie dzialac
- }
- }
- ///
- }
- }
- bool sprawdz_nawiasy()
- {
- int nawiasy=0;
- for (int i=0; i<input.length(); i++)
- {
- if (input[i] == '(')
- {
- nawiasy++;
- }
- else if (input[i] == ')')
- {
- nawiasy--;
- if (nawiasy < 0)
- {
- error();
- }
- }
- }
- if (nawiasy!=0)
- {
- return false;
- }
- else
- {
- return true;
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement