parser: treat f<mod.Type> as generic call not `<` operator (#8938)

pull/8989/head
zakuro 2021-02-26 16:05:00 +09:00 committed by GitHub
parent 5aebd646bb
commit 89c82ff8e2
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 17 additions and 5 deletions

View File

@ -1121,15 +1121,20 @@ fn (p &Parser) is_generic_call() bool {
} else { } else {
false false
} }
tok2 := p.peek_token(2)
tok3 := p.peek_token(3)
tok4 := p.peek_token(4)
tok5 := p.peek_token(5)
// use heuristics to detect `func<T>()` from `var < expr` // use heuristics to detect `func<T>()` from `var < expr`
return !lit0_is_capital && p.peek_tok.kind == .lt && (match p.peek_token(2).kind { return !lit0_is_capital && p.peek_tok.kind == .lt && (match tok2.kind {
.name { .name {
// maybe `f<int>`, `f<map[`, f<string, // (`f<int>`, `f<string,`) || (`f<mod.Type>`, `<mod.Type,`) || `f<map[`,
(p.peek_token(2).kind == .name && p.peek_token(3).kind in [.gt, .comma]) || (p.peek_token(2).lit == 'map' && p.peek_token(3).kind == .lsbr)
tok3.kind in [.gt, .comma] || (tok3.kind == .dot && tok4.kind == .name && tok5.kind in [.gt, .comma]) || (tok2.lit == 'map' && tok3.kind == .lsbr)
} }
.lsbr { .lsbr {
// maybe `f<[]T>`, assume `var < []` is invalid // maybe `f<[]T>`, assume `var < []` is invalid
p.peek_token(3).kind == .rsbr tok3.kind == .rsbr
} }
else { else {
false false

View File

@ -23,6 +23,8 @@ fn test_identity() {
assert simple<[]int>([1])[0] == 1 assert simple<[]int>([1])[0] == 1
assert simple<map[string]string>({'a':'b'})['a'] == 'b' assert simple<map[string]string>({'a':'b'})['a'] == 'b'
assert simple<simplemodule.Data>(simplemodule.Data{value: 0}).value == 0
} }
fn test_plus() { fn test_plus() {

View File

@ -11,3 +11,8 @@ pub fn imul(x int, y int) int {
pub struct ThisIsGeneric<T> { pub struct ThisIsGeneric<T> {
msg T msg T
} }
pub struct Data {
pub:
value int
}