use super::types::VarType;
use std::collections::HashMap;
#[derive(Debug, Clone)]
pub enum AST {
Program {
declarations: Vec<Declaration>,
objective: Objective,
constraints: Vec<Constraint>,
},
VarDecl {
name: String,
var_type: VarType,
domain: Option<Domain>,
attributes: HashMap<String, Value>,
},
Expr(Expression),
Stmt(Statement),
}
#[derive(Debug, Clone)]
pub enum Declaration {
Variable {
name: String,
var_type: VarType,
domain: Option<Domain>,
attributes: HashMap<String, Value>,
},
Parameter {
name: String,
value: Value,
description: Option<String>,
},
Set { name: String, elements: Vec<Value> },
Function {
name: String,
params: Vec<String>,
body: Box<Expression>,
},
}
#[derive(Debug, Clone)]
pub enum Domain {
Range { min: f64, max: f64 },
Set { values: Vec<Value> },
IndexSet { set_name: String },
}
#[derive(Debug, Clone)]
pub enum Value {
Number(f64),
Boolean(bool),
String(String),
Array(Vec<Self>),
Tuple(Vec<Self>),
}
#[derive(Debug, Clone)]
pub enum Objective {
Minimize(Expression),
Maximize(Expression),
MultiObjective {
objectives: Vec<(ObjectiveType, Expression, f64)>,
},
}
#[derive(Debug, Clone)]
pub enum ObjectiveType {
Minimize,
Maximize,
}
#[derive(Debug, Clone)]
pub struct Constraint {
pub name: Option<String>,
pub expression: ConstraintExpression,
pub tags: Vec<String>,
}
#[derive(Debug, Clone)]
pub enum ConstraintExpression {
Comparison {
left: Expression,
op: ComparisonOp,
right: Expression,
},
Logical { op: LogicalOp, operands: Vec<Self> },
Quantified {
quantifier: Quantifier,
variables: Vec<(String, String)>, constraint: Box<Self>,
},
Implication {
condition: Box<Self>,
consequence: Box<Self>,
},
Counting {
variables: Vec<String>,
op: ComparisonOp,
count: Expression,
},
}
#[derive(Debug, Clone, PartialEq, Eq)]
pub enum ComparisonOp {
Equal,
NotEqual,
Less,
Greater,
LessEqual,
GreaterEqual,
}
#[derive(Debug, Clone)]
pub enum LogicalOp {
And,
Or,
Not,
Xor,
}
#[derive(Debug, Clone)]
pub enum Quantifier {
ForAll,
Exists,
ExactlyOne,
AtMostOne,
AtLeastOne,
}
#[derive(Debug, Clone)]
pub enum Expression {
Literal(Value),
Variable(String),
IndexedVar { name: String, indices: Vec<Self> },
BinaryOp {
op: BinaryOperator,
left: Box<Self>,
right: Box<Self>,
},
UnaryOp {
op: UnaryOperator,
operand: Box<Self>,
},
FunctionCall { name: String, args: Vec<Self> },
Aggregation {
op: AggregationOp,
variables: Vec<(String, String)>, expression: Box<Self>,
},
Conditional {
condition: Box<ConstraintExpression>,
then_expr: Box<Self>,
else_expr: Box<Self>,
},
}
#[derive(Debug, Clone)]
pub enum BinaryOperator {
Add,
Subtract,
Multiply,
Divide,
Power,
Modulo,
}
#[derive(Debug, Clone)]
pub enum UnaryOperator {
Negate,
Abs,
Sqrt,
Exp,
Log,
}
#[derive(Debug, Clone)]
pub enum AggregationOp {
Sum,
Product,
Min,
Max,
Count,
}
#[derive(Debug, Clone)]
pub enum Statement {
Assignment { target: String, value: Expression },
If {
condition: ConstraintExpression,
then_branch: Vec<Self>,
else_branch: Option<Vec<Self>>,
},
For {
variable: String,
set: String,
body: Vec<Self>,
},
}