Consider the following Swift expression
println(Generic<Foo, Bar>(1))
Normally, one would read this as a generic call to the constructor Generic<Foo, Bar>
with the arguments (1)
.
println( Generic<Foo,Bar>(1) )
However, when re-arranging the tokens a bit, it could also represent two separate comparisons, for example if Generic
and Foo
were some poorly named numeric variables:
println(Generic < Foo, Bar > (1))
// or, with proper parenthesis
println((Generic < Foo), (Bar > 1))
What we can observe here is that an expression with a generic constructor like this is highly ambiguous, and not easy to disambiguate even for humans. The problem here is that Swift doesn't have a new
keyword for constructors, which makes them ambiguous with method calls and operators in some cases. Thus, I am interested in how the Swift compiler (parser) manages to disambiguate the above expressions. Is the way it is parsed dependant on the context (types, variables, functions) or can it be resolved by the parser?
The answer is simple: The compiler simply does't allow you to declare these variables:
struct Generic<T, U> {
init(_ i: Int) {}
}
struct Foo {}
struct Bar {}
print(Generic<Foo, Bar>(1))
// error
let Foo = 0 // invalid redeclaration of Foo
let Bar = 3 // invalid redeclaration of Bar
let Generic = 5 // invalid redeclaration of Generic
print(Generic<Foo, Bar>(1))
Making either the variables or the type declarations in another source file the current declaration "overrides" the other one.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With