This project is a C++ implementation of a mathematical expression parser and evaluator. It takes an input string representing a mathematical expression, tokenizes it, parses it into an Abstract Syntax Tree (AST), and then evaluates the result. The parser supports basic arithmetic operations such as addition, subtraction, multiplication, division, exponentiation, and modulus, along with parentheses for grouping and unary negation. This could easily be extended to support common functions such as sine and cosine.
- Parses mathematical expressions into an Abstract Syntax Tree (AST)
- Supports basic arithmetic operations:
+
,-
,*
,/
,%
,^
- Handles unary negation and parentheses for grouping
- Error handling for syntax errors like unmatched parentheses or division by zero
- Clean, modular design with a lexer, parser, and evaluator
To build and run this project, you will need:
- A C++ compiler supporting C++11 or later (e.g., GCC, Clang)
make
(optional, if you use a Makefile)- Git (to clone the repository)
-
Clone the repository:
git clone https://github.com/programmerstevie/cppMather.git cd cppMather
-
Compile the project:
If you're using
make
, simply run:make
Alternatively, compile the source files manually:
g++ -std=c++11 -o parser main.cpp lexer.cpp parser.cpp evaluator.cpp
After compiling the project, run the executable and enter a mathematical expression to evaluate:
-
Run the executable:
./parser
-
Input a mathematical expression:
For example:
(5 + 3) * 2 - 4 ^ 2
-
The program will output:
(5 + 3) * 2 - 4 ^ 2 = -4
includes.hpp
: Centralized file for including necessary standard library headers.lexer.hpp
/lexer.cpp
: Responsible for tokenizing the input string into meaningful tokens (numbers, operators, parentheses).parser.hpp
/parser.cpp
: Processes tokens into an Abstract Syntax Tree (AST) using operator precedence and associativity rules.evaluator.hpp
/evaluator.cpp
: Evaluates the AST and computes the result of the expression.token.hpp
/token.cpp
: Defines the different types of tokens used in the program (integer tokens, operator tokens, parenthesis tokens).main.cpp
: The entry point of the program, showing an example of how to go from an expression string to its evaluation.
The lexer (lexer.cpp
) breaks down the input string into tokens representing integers, operators, and parentheses. For example, the expression 3 + (5 * 2)
would be tokenized into:
IntToken(3)
BinaryOpToken(+)
ParenToken(()
IntToken(5)
BinaryOpToken(*)
IntToken(2)
ParenToken())
The parser (parser.cpp
) uses a shunting yard algorithm to convert the tokens into an Abstract Syntax Tree (AST). It ensures that operations are applied in the correct order by respecting operator precedence and associativity.
For example, for the input 5 + 3 * 2
, the AST will look like this:
+
/ \
5 *
/ \
3 2
The evaluator (evaluator.cpp
) recursively evaluates the AST to compute the final result of the expression. For example, the AST for 5 + 3 * 2
will be evaluated as:
- Multiply
3 * 2
to get6
. - Add
5 + 6
to get11
.
The parser and evaluator have several built-in error checks to ensure that the input expression is valid:
- Unmatched Parentheses: The parser checks for balanced parentheses.
- Division by Zero: The evaluator checks for division by zero and terminates with an error if encountered.
- Invalid Tokens: The lexer and token constructors validate that only valid tokens are processed.
The prettyPrint()
function in evaluator.cpp
can convert an AST back into a human-readable string, showing the expression in standard infix notation.
Contributions are welcome! If you have suggestions or improvements, feel free to fork the repository and submit a pull request.
- Fork the project
- Create your feature branch (
git checkout -b feature/AmazingFeature
) - Commit your changes (
git commit -m 'Add some AmazingFeature'
) - Push to the branch (
git push origin feature/AmazingFeature
) - Open a pull request
Distributed under the MIT License. See LICENSE
for more information.