Ensure that division is left assosiative in UDQ parser
This commit is contained in:
parent
d9a7d6326f
commit
80a023794e
@ -140,21 +140,39 @@ UDQASTNode UDQParser::parse_pow() {
|
||||
|
||||
|
||||
UDQASTNode UDQParser::parse_mul() {
|
||||
auto left = this->parse_pow();
|
||||
auto current = this->current();
|
||||
if (this->empty())
|
||||
return left;
|
||||
std::vector<UDQASTNode> nodes;
|
||||
{
|
||||
std::unique_ptr<UDQASTNode> current_node;
|
||||
while (true) {
|
||||
auto node = this->parse_pow();
|
||||
if (current_node) {
|
||||
current_node->set_right(node);
|
||||
nodes.push_back(*current_node);
|
||||
} else
|
||||
nodes.push_back(node);
|
||||
|
||||
if (current.type == UDQTokenType::binary_op_mul || current.type == UDQTokenType::binary_op_div) {
|
||||
this->next();
|
||||
if (this->empty())
|
||||
return UDQASTNode(UDQTokenType::error);
|
||||
if (this->empty())
|
||||
break;
|
||||
|
||||
auto right = this->parse_mul();
|
||||
return UDQASTNode(current.type, current.value, left, right);
|
||||
auto current_token = this->current();
|
||||
if (current_token.type == UDQTokenType::binary_op_mul || current_token.type == UDQTokenType::binary_op_div) {
|
||||
current_node.reset( new UDQASTNode(current_token.type, current_token.value) );
|
||||
this->next();
|
||||
if (this->empty())
|
||||
return UDQASTNode( UDQTokenType::error );
|
||||
} else break;
|
||||
}
|
||||
}
|
||||
|
||||
return left;
|
||||
UDQASTNode top_node = nodes.back();
|
||||
if (nodes.size() > 1) {
|
||||
UDQASTNode * current = &top_node;
|
||||
for (std::size_t index = nodes.size() - 1; index > 0; index--) {
|
||||
current->set_left(nodes[index - 1]);
|
||||
current = current->get_left();
|
||||
}
|
||||
}
|
||||
return top_node;
|
||||
}
|
||||
|
||||
|
||||
|
@ -2264,3 +2264,18 @@ TSTEP
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
BOOST_AUTO_TEST_CASE(UDQ_DIV_TEST) {
|
||||
KeywordLocation location;
|
||||
UDQFunctionTable udqft;
|
||||
UDQParams udqp;
|
||||
UDQDefine def_div(udqp, "FU", location, {"128", "/", "2", "/", "4", "/", "8"});
|
||||
SummaryState st(std::chrono::system_clock::now());
|
||||
UDQState udq_state(udqp.undefinedValue());
|
||||
UDQContext context(udqft, st, udq_state);
|
||||
|
||||
auto res_div = def_div.eval(context);
|
||||
BOOST_CHECK_EQUAL( res_div[0].get() , 2.0);
|
||||
}
|
||||
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user