pddl_parser/domain/
typing.rs

1use std::string::ToString;
2
3use nom::branch::alt;
4use nom::combinator::{map, opt};
5use nom::multi::{many0, many1};
6use nom::sequence::{delimited, pair, preceded};
7use nom::IResult;
8use serde::{Deserialize, Serialize};
9
10use super::typedef::TypeDef;
11use crate::error::ParserError;
12use crate::lexer::{Token, TokenStream};
13use crate::tokens::id;
14
15/// A type is either a simple type or one of the list of specified types.
16#[derive(Debug, Deserialize, Serialize, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
17pub enum Type {
18    /// The type is a simple type.
19    Simple(String),
20    /// The type must be one of the specified types.
21    Either(Vec<String>),
22}
23
24impl From<&str> for Type {
25    fn from(s: &str) -> Self {
26        Type::Simple(s.to_string())
27    }
28}
29
30impl Default for Type {
31    fn default() -> Self {
32        "object".into()
33    }
34}
35
36impl Type {
37    /// Parse a type from a token stream.
38    pub fn parse_type(input: TokenStream) -> IResult<TokenStream, Type, ParserError> {
39        log::debug!("BEGIN > parse_type {:?}", input.span());
40        let (output, type_) = alt((
41            map(id, Type::Simple),
42            map(
43                delimited(Token::OpenParen, preceded(Token::Either, many1(id)), Token::CloseParen),
44                Type::Either,
45            ),
46        ))(input)?;
47        log::debug!("END < parse_type {:?}", output.span());
48        Ok((output, type_))
49    }
50
51    /// Parse a list of types from a token stream.
52    pub fn parse_types(input: TokenStream) -> IResult<TokenStream, Vec<TypeDef>, ParserError> {
53        log::debug!("BEGIN > parse_types {:?}", input.span());
54        let (output, types) = delimited(
55            Token::OpenParen,
56            preceded(Token::Types, many0(pair(many1(id), opt(preceded(Token::Dash, id))))),
57            Token::CloseParen,
58        )(input)?;
59        let types = types
60            .into_iter()
61            .flat_map(|(names, parent)| {
62                names.into_iter().map(move |name| TypeDef {
63                    name,
64                    parent: parent.clone(),
65                })
66            })
67            .collect();
68        log::debug!("END < parse_types {:?}", output.span());
69        Ok((output, types))
70    }
71
72    /// Convert the type to PDDL.
73    pub fn to_pddl(&self) -> String {
74        match self {
75            Type::Simple(s) => s.to_string(),
76            Type::Either(v) => format!("(either {})", v.join(" ")),
77        }
78    }
79}