Skip to content

[Feature Request] Operator Precedence Climbing #78

@cch123

Description

@cch123
{
//------ start
package main

type CompExpr struct {
    left string
    op string
    right string
}

type LogicExpr struct {
    left interface{}
    op string
    right interface{}
}

func main() {
    if len(os.Args) != 2 {
        log.Fatal("Usage: calculator 'EXPR'")
    }
    got, err := ParseReader("", strings.NewReader(os.Args[1]))
    if err != nil {
        log.Fatal(err)
    }
    fmt.Printf("%#v\n", got)
}

// ------ end
}

Input <- expr:Expr EOF {
    return expr, nil
}

Expr <- LogicExpr / Atom

LogicExpr <- _ atom:Atom _ op: LogicOp _ expr: Expr _ {
    return  LogicExpr {left : atom, op : op.(string), right: expr}, nil
}

Atom <- '(' expr:Expr ')' {
    return expr, nil
} / _ field: Ident _ op:BinOp _ value:Value _{
    return CompExpr{left : field.(string), op: op.(string), right : value.(string)}, nil
}

LogicOp <- ("and" / "or"){
    return string(c.text), nil
}

BinOp <- ("!=" / ">=" / "<=" / "=" / "<>" / ">" / "<") {
    return string(c.text),nil
}

Ident <- [a-zA-Z][a-zA-Z0-9]* {
    return string(c.text),nil
}

Value <- [0-9]+ {
    return string(c.text),nil
}

_ "whitespace" <- [ \n\t\r]*

EOF <- !.

The right recursion grammar will auto-generate right association

If pigeon can implement precedence climbing or something else, it will be very convenient ~

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions