use super::common::*;
use super::fof::FOFTerm;
use super::thf::{LogicSpecification, NonClassicalOperator};
#[derive(Debug, Clone, PartialEq)]
pub enum TFFStatement<'a> {
Logical(TFFFormula<'a>),
Typing(TFFTyping<'a>),
Sequent(Vec<TFFFormula<'a>>, Vec<TFFFormula<'a>>),
Logic(LogicSpecification<'a>),
}
#[derive(Debug, Clone, PartialEq)]
pub struct TFFTyping<'a> {
pub symbol: TypedSymbol<'a>,
pub typ: TFFType<'a>,
}
#[derive(Debug, Clone, PartialEq)]
pub enum TypedSymbol<'a> {
Atom(AtomicWord<'a>),
Defined(DefinedWord<'a>),
}
#[derive(Debug, Clone, PartialEq)]
pub enum TFFFormula<'a> {
Atomic(TFFAtomicFormula<'a>),
Negation(Box<TFFFormula<'a>>),
Quantified {
quantifier: Quantifier,
variables: Vec<TFFVariable<'a>>,
formula: Box<TFFFormula<'a>>,
},
TypeQuantified {
quantifier: TypeQuantifier,
type_variables: Vec<&'a str>,
formula: Box<TFFFormula<'a>>,
},
Binary {
left: Box<TFFFormula<'a>>,
connective: BinaryConnective,
right: Box<TFFFormula<'a>>,
},
Equality(TFFTerm<'a>, TFFTerm<'a>),
Inequality(TFFTerm<'a>, TFFTerm<'a>),
Parens(Box<TFFFormula<'a>>),
Conditional {
condition: Box<TFFFormula<'a>>,
then_branch: Box<TFFFormula<'a>>,
else_branch: Box<TFFFormula<'a>>,
},
Let {
definitions: Vec<TFFLetDef<'a>>,
body: Box<TFFLetBody<'a>>,
},
NonClassical {
operator: NonClassicalOperator<'a>,
formula: Box<TFFFormula<'a>>,
},
}
#[derive(Debug, Clone, PartialEq)]
pub struct TFFVariable<'a> {
pub name: &'a str,
pub typ: Option<TFFType<'a>>,
}
impl<'a> TFFVariable<'a> {
pub fn new(name: &'a str) -> Self {
TFFVariable { name, typ: None }
}
pub fn typed(name: &'a str, typ: TFFType<'a>) -> Self {
TFFVariable {
name,
typ: Some(typ),
}
}
}
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum TypeQuantifier {
ForallType,
ExistsType,
}
impl TypeQuantifier {
pub fn as_str(&self) -> &'static str {
match self {
TypeQuantifier::ForallType => "!>",
TypeQuantifier::ExistsType => "?*",
}
}
}
#[derive(Debug, Clone, PartialEq)]
pub enum TFFAtomicFormula<'a> {
Plain(AtomicWord<'a>, Vec<TFFTerm<'a>>),
Defined(DefinedWord<'a>, Vec<TFFTerm<'a>>),
System(SystemWord<'a>, Vec<TFFTerm<'a>>),
True,
False,
Variable(&'a str),
}
#[derive(Debug, Clone, PartialEq)]
pub enum TFFTerm<'a> {
Variable(&'a str),
Function(AtomicWord<'a>, Vec<TFFTerm<'a>>),
DefinedFunction(DefinedWord<'a>, Vec<TFFTerm<'a>>),
SystemFunction(SystemWord<'a>, Vec<TFFTerm<'a>>),
Number(Number<'a>),
DistinctObject(&'a str),
Conditional {
condition: Box<TFFFormula<'a>>,
then_branch: Box<TFFTerm<'a>>,
else_branch: Box<TFFTerm<'a>>,
},
Let {
definitions: Vec<TFFLetDef<'a>>,
body: Box<TFFTerm<'a>>,
},
Tuple(Vec<TFFTerm<'a>>),
FormulaAsTerm(Box<TFFFormula<'a>>),
Parens(Box<TFFTerm<'a>>),
}
#[derive(Debug, Clone, PartialEq)]
pub struct TFFLetDef<'a> {
pub symbol: AtomicWord<'a>,
pub type_args: Vec<&'a str>,
pub params: Vec<TFFVariable<'a>>,
pub typ: Option<TFFType<'a>>,
pub definition: TFFLetBody<'a>,
}
#[derive(Debug, Clone, PartialEq)]
pub enum TFFLetBody<'a> {
Formula(TFFFormula<'a>),
Term(TFFTerm<'a>),
}
#[derive(Debug, Clone, PartialEq)]
pub enum TFFType<'a> {
Atomic(AtomicWord<'a>),
Defined(DefinedType),
Variable(&'a str),
Function {
args: Vec<TFFType<'a>>,
result: Box<TFFType<'a>>,
},
Application(Box<TFFType<'a>>, Vec<TFFType<'a>>),
Tuple(Vec<TFFType<'a>>),
Quantified {
variables: Vec<&'a str>,
typ: Box<TFFType<'a>>,
},
Parens(Box<TFFType<'a>>),
}
impl<'a> TFFType<'a> {
pub fn individual() -> Self {
TFFType::Defined(DefinedType::I)
}
pub fn boolean() -> Self {
TFFType::Defined(DefinedType::O)
}
pub fn ttype() -> Self {
TFFType::Defined(DefinedType::TType)
}
}
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum DefinedType {
I,
O,
Int,
Rat,
Real,
TType,
}
impl DefinedType {
pub fn as_str(&self) -> &'static str {
match self {
DefinedType::I => "$i",
DefinedType::O => "$o",
DefinedType::Int => "$int",
DefinedType::Rat => "$rat",
DefinedType::Real => "$real",
DefinedType::TType => "$tType",
}
}
pub fn parse(s: &str) -> Option<Self> {
match s {
"$i" | "i" => Some(DefinedType::I),
"$o" | "o" => Some(DefinedType::O),
"$int" | "int" => Some(DefinedType::Int),
"$rat" | "rat" => Some(DefinedType::Rat),
"$real" | "real" => Some(DefinedType::Real),
"$tType" | "tType" => Some(DefinedType::TType),
_ => None,
}
}
}
impl<'a> From<FOFTerm<'a>> for TFFTerm<'a> {
fn from(term: FOFTerm<'a>) -> Self {
match term {
FOFTerm::Variable(v) => TFFTerm::Variable(v),
FOFTerm::Function(f, args) => {
TFFTerm::Function(f, args.into_iter().map(Into::into).collect())
}
FOFTerm::DefinedFunction(f, args) => {
TFFTerm::DefinedFunction(f, args.into_iter().map(Into::into).collect())
}
FOFTerm::SystemFunction(f, args) => {
TFFTerm::SystemFunction(f, args.into_iter().map(Into::into).collect())
}
FOFTerm::Number(n) => TFFTerm::Number(n),
FOFTerm::DistinctObject(s) => TFFTerm::DistinctObject(s),
}
}
}