2

In my project i need to take an expression input from user as string and then show the result of the expression. I am taking the input as follows

char address[100] = {NULL};
fgets(address, 100, stdin); //take the expression as input here

say user wrote the expression as

address = " 1+5+9" . 

What i need to do is to show the result of the expression. I can do this by separating each number and then doing the calculation. But i just wanted to know is there any better way to do this?

Griwes
  • 8,805
  • 2
  • 43
  • 70
  • 4
    Look up postfix expression evaluation and usage of stack – Aditya Kumar Pandey Jun 19 '12 at 12:57
  • 1
    You can start by using `std::cin` or `std::getline`, as well as `std::string`. – chris Jun 19 '12 at 12:58
  • Nope, this is the best way to do it. In fact, to evaluate complex mathematical expressions like `(3+2) * (1 - (3 * 2 + 1) / 4 + 1 ^ 5)` you need to implement a recursive descent parser using something like YACC or Bison. **PS:** This is hard to do. – Hans Z Jun 19 '12 at 12:59
  • 3
    Stroustrup devotes an entire chapter to this problem in "The C++ programming language". – Happy Green Kid Naps Jun 19 '12 at 13:00
  • @HappyGreenKidNaps, I like that chapter. I learned a lot from it. – Michael Kristofik Jun 19 '12 at 13:02
  • @Hans, the best way to evaluate complex mathematical expressions is still stack and usage of Reverse Polish Notation. RDP is way to complex for such simple evaluation. **PS**: your example does not qualify as "complex mathematical expression". – Griwes Jun 19 '12 at 13:02
  • @Griwes `3 * 2 + 1` is hard to parse because of order of operations, as is `/ 4 + 1 ^ 5`. RPN is nice but unless if you are forcing your users to write in RPN then you are going to have to write a parser that takes standard math expressions and turn it into RPN. – Hans Z Jun 19 '12 at 13:06
  • @Hans, it's not hard to parse expressions with operators with different priorities not being separated by brackets. It's really simple algorithm, which is, I think, described on one of wikipedia pages (I'm 100% sure it's on Polish version of RPN article, not sure whether or where on English version). – Griwes Jun 19 '12 at 13:18
  • Thanks guys for helping. Now understand there is no simple way except parsing. Though i am new but i will give it a try. –  Jun 19 '12 at 13:34
  • @Hans You don't need Yacc or Bison---they're probably overkill for something this simple. And they don't generate recursive descent parsers---I would use a (hand written) recursive descent parser here. They're extremely simple to write. – James Kanze Jun 19 '12 at 14:28
  • Also, you shouldn't use `NULL` to initialize an array of `char`. `NULL` is traditionally used for pointers, not `char`, and a good compiler will generate a warning if you use it in a non-pointer context. (Of course, you should be using `std::string` anyway.) – James Kanze Jun 19 '12 at 14:30

2 Answers2

3

It's sounds like you're looking for a C++ equivalent to something like eval in JavaScript. Unfortunately, C++ doesn't have one. Parsing the expression by hand is the best you can do.

If you have access to The C++ Programming Language book, chapter 6 covers how one would write a simple calculator program, solving the same problem you have.

Michael Kristofik
  • 34,290
  • 15
  • 75
  • 125
  • 2
    Thanks guys for helping. Now understand there is no simple way except parsing. Though i am new but i will give it a try. –  Jun 19 '12 at 13:34
  • 1
    Being new to programming is a great reason to try writing a parser by hand, even if C++ had an automated way to do it. You'll learn a lot from it. – Michael Kristofik Jun 19 '12 at 14:11
0

There are several approaches for doing this, one of the most popular ways, and in my personal oppinion most elegant ways, is to use a recursive descent parser. There are lots of useful guides to doing this on the web. A simple google search led me to:

Also these Stack Overflow posts:

The problem with simply seperating the numbers and then doing the calculation is the problems that occur when you allow multiplication and generally needs to consider the order of operators.

Community
  • 1
  • 1
Tommy Andersen
  • 7,165
  • 1
  • 31
  • 50