ProgrammingThis forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.
Notices
Welcome to LinuxQuestions.org, a friendly and active Linux Community.
You are currently viewing LQ as a guest. By joining our community you will have the ability to post topics, receive our newsletter, use the advanced search, subscribe to threads and access many other special features. Registration is quick, simple and absolutely free. Join our community today!
Note that registered members see fewer ads, and ContentLink is completely disabled once you log in.
If you have any problems with the registration process or your account login, please contact us. If you need to reset your password, click here.
Having a problem logging in? Please visit this page to clear all LQ-related cookies.
Get a virtual cloud desktop with the Linux distro that you want in less than five minutes with Shells! With over 10 pre-installed distros to choose from, the worry-free installation life is here! Whether you are a digital nomad or just looking for flexibility, Shells can put your Linux machine on the device that you want to use.
Exclusive for LQ members, get up to 45% off per month. Click here for more info.
Sure, but what for - if Java parser already does this ?
The point is not to write code if it's already available.
I agree with you in many contexts. The OP wrote:
Quote:
Originally Posted by rabbit2345
... but i am curious, is there a way to split it multiple ways and solve?
I think we are all curious about how to solve problems at more than one level -- we may not always be writing in Java, for example, and so may not have something already written for us. I have found that knowing more than one way to solve a problem often comes in handy.
We can be constructively lazy on one hand, and, on the other hand, we can investigate deeper -- we can look at algorithms upon which are based extant facilities. Those facilities may be available to us through libraries. Sometimes we don't care how something performs a task. Sometimes we might.
Let us take a step back: if we are only interested in evaluating an arithmetic expression, there are many higher-level solutions that do not involve writing any code ... cheers, makyo
I think we are all curious about how to solve problems at more than one level -- we may not always be writing in Java, for example, and so may not have something already written for us. I have found that knowing more than one way to solve a problem often comes in handy.
We can be constructively lazy on one hand, and, on the other hand, we can investigate deeper -- we can look at algorithms upon which are based extant facilities. Those facilities may be available to us through libraries. Sometimes we don't care how something performs a task. Sometimes we might.
Let us take a step back: if we are only interested in evaluating an arithmetic expression, there are many higher-level solutions that do not involve writing any code ... cheers, makyo
No, that is not possible. Anything you enter on the command line is read as a String - and the problem is that you cannot perform math on a String without first breaking it up and converting the numerical parts into integer of floating-point values. This is very easy to find out: if you make x and you assign "1/2+2", you will run into an exception.
> like jonaskoelker said, what if someone put in 1+2*3? that would split to 1+(2*3)
If you only allow binary operators and no parenthesis, I'd go for the bottom-up solution:
1. Split the string into a linked list ["1", "+", "2", "*", "3"].
2. For each precedence level of operators (i.e. first for "*" and "/", next for "+" and "-"):
Run left-to-right, whenever you see [number, one of your operators, number] in your array, evaluate that subexpression and replace the sublist with its result.
3. Your list should have one number left now. That's your result.
You probably want to specify negative numbers with something other than "-", otherwise you have to parse "-3*-2--4".
Otherwise, find a good, long introduction to parsing. Find the grammar for a few languages you know (java, c, python) and study how they parse things [or if you rather want to find things out on your own, skip this step]. Find a parser tool, use it to parse expressions.
It'll serve you well later to know this. If you don't know regular expressions, you may want to learn about those if you want to write a good lexer [which efficient parsing really requires].
No, that is not possible. See my previous post for details. Whatever you enter on the command line is simply a constant value - but operators cannot be simply constant values, they need to have a special meaning. This will not happen automatically so it is up to you to split and sort to output into numbers and operators and turn those into a real expression.
but anyway, is there a more efficient way to do this than to split the string into 6 different parts and do the math that way?
I'm pretty sure I'm not the first person to want to do this kind of thing
You could use a stream, which would allow you to read in one character at a time but then you'd still have to figure out which are numbers and which are operators. If you prefer being lazy, then you could pass the expression to another application such as bc - but that would be cheating and it would most definitely only work on something like Linux (because you can't expect Mac or Windows users to have that specific application installed). And - obviously - if bc does some things differently, you're back to where you started as you'll need to make certain modifications before passing the expression on. In short, no, there isn't any magic.
so if I enter 1+2+3, it will set a variable to 1+2+3, and solve?
It's possible to invoke javac from a java program: it's available as a class. I think you have to create code in a string like this:
Code:
"class Evaluator {
public static int eval() {
return (" + expr + ");
}
}"
Then get the resulting class, and invoke the eval method using introspection (I'm not sure). Remember to remove all references to the class unless you want to leak memory. I think maybe the class loader stores a copy, but I wouldn't know.
It's possible to invoke javac from a java program: it's available as a class. I think you have to create code in a string like this:
Code:
"class Evaluator {
public static int eval() {
return (" + expr + ");
}
}"
Then get the resulting class, and invoke the eval method using introspection (I'm not sure). Remember to remove all references to the class unless you want to leak memory. I think maybe the class loader stores a copy, but I wouldn't know.
It's already been suggested without going into details:
I seems to me that the OP is trying to gain an understanding of parsers, grammars, and such related concepts (even though he may not know this). One traditional way of generating such codes is through the use of tools such as lex/flex and yacc/bison, which are good at generating lexical analyzers and parsers in C. For java, Sun has produced the equivalent tool set 'Jack' (Yacc for Java). Using tools such as this can be quite instructive, as well as productive.
While I've not used Jack, it is allegedly equivalent to flex & bison. The two have separate but related jobs, that divide the process into separate steps. The first step is to tokenize the input into generalized types of data, such as specific operators (+, -, *, /, etc.), numeric types (integers, reals, etc), and other elements such as parentheses, text (for function names like trigonometry, logs, etc.). The second step is to assemble the component parts into an expression and then evaluate it. Flex & bison (for Java, Jack) generate code that correctly performs these functions, as well as some glue code that makes them work together, if desired. The tools take a special input format using regular expressions and other notation to describe the way the input stream is to broken into tokens (the lexical analyzer part), and then evaluated as an expression. Understanding these tools will give significant insight into expression evaluation.
I seems to me that the OP is trying to gain an understanding of parsers, grammars, and such related concepts (even though he may not know this). One traditional way of generating such codes is through the use of tools such as lex/flex and yacc/bison, which are good at generating lexical analyzers and parsers in C. For java, Sun has produced the equivalent tool set 'Jack' (Yacc for Java). Using tools such as this can be quite instructive, as well as productive.
While I've not used Jack, it is allegedly equivalent to flex & bison. The two have separate but related jobs, that divide the process into separate steps. The first step is to tokenize the input into generalized types of data, such as specific operators (+, -, *, /, etc.), numeric types (integers, reals, etc), and other elements such as parentheses, text (for function names like trigonometry, logs, etc.). The second step is to assemble the component parts into an expression and then evaluate it. Flex & bison (for Java, Jack) generate code that correctly performs these functions, as well as some glue code that makes them work together, if desired. The tools take a special input format using regular expressions and other notation to describe the way the input stream is to broken into tokens (the lexical analyzer part), and then evaluated as an expression. Understanding these tools will give significant insight into expression evaluation.
LinuxQuestions.org is looking for people interested in writing
Editorials, Articles, Reviews, and more. If you'd like to contribute
content, let us know.