use super::{field_access, function_call, integer_literal, rvalue::RValue, variable_ref};
use nom::{branch::alt, bytes::complete::tag, combinator::map, sequence::tuple, IResult};
#[derive(Debug, Eq, PartialEq, Clone, Hash)]
pub struct UnaryOperatorResult {
pub operator: String,
pub operand: Box<RValue>,
}
pub fn higher_than_unary_operator_result(code: &str) -> IResult<&str, RValue> {
alt((
map(function_call::parse, RValue::FunctionCall),
map(field_access::parse, RValue::FieldAccess),
map(variable_ref::parse, RValue::VariableRef),
map(integer_literal::parse, RValue::IntegerLiteral),
))(code)
}
pub fn parse(code: &str) -> IResult<&str, UnaryOperatorResult> {
map(
tuple((
alt((tag("+"), tag("-"), tag("!"), tag("~"))),
higher_than_unary_operator_result,
)),
|(op, operand)| UnaryOperatorResult {
operator: op.to_string(),
operand: Box::new(operand),
},
)(code)
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn can_parse() {
let result = parse("-a").unwrap().1;
assert_eq!(result.operator, "-");
}
}