Pan Hania
Pan Hania

Reputation: 478

Why cannot I use methods on brace-style macro expression in return position?

Consider the following example:

macro_rules! some {
    { $expr:expr } => { Some($expr) };
}

fn foo() -> Option<i32> {
    some! {
        42
    }.map(std::convert::identity)
}

This code will fail to compile with the following error:

error: expected expression, found `.`

However, the compiler will accept the code if I bind the result to a temporary variable:

fn foo() -> Option<i32> {
    let result = some! {
        42
    }.map(std::convert::identity);

    result
}

If I remove the invocation of map the code also compiles without issues:

fn foo() -> Option<i32> {
    some! {
        42
    }
}

Parenthesis and bracket variants of macro invocation also work fine:

fn foo() -> Option<i32> {
    some!(42).map(std::convert::identity)
}
fn foo() -> Option<i32> {
    some![42].map(std::convert::identity)
}

I presume there is some ambiguity when using curly braces but I don't exactly see what it can be. What is the problem here?

Upvotes: 1

Views: 882

Answers (1)

Jeff Garrett
Jeff Garrett

Reputation: 7383

This is precisely: https://github.com/rust-lang/rust/issues/40100

There are several more macro parsing issues that may be interesting: https://github.com/rust-lang/rust/issues?q=is%3Aopen+label%3AA-macros+label%3AA-parser

Upvotes: 2

Related Questions