diff options
author | buraq <buraq@epfl.ch> | 2003-11-04 12:45:28 +0000 |
---|---|---|
committer | buraq <buraq@epfl.ch> | 2003-11-04 12:45:28 +0000 |
commit | 76ff2cfcc565b5028352a2b6584fee321f14a375 (patch) | |
tree | 47ea3562b3a3348895336d01637d2f641f434aa3 | |
parent | a4d3dba63bede16dfad42eaf0870cbd49bf9c3c9 (diff) | |
download | scala-76ff2cfcc565b5028352a2b6584fee321f14a375.tar.gz scala-76ff2cfcc565b5028352a2b6584fee321f14a375.tar.bz2 scala-76ff2cfcc565b5028352a2b6584fee321f14a375.zip |
fixed erroneous handling of typed patters
-rw-r--r-- | sources/scalac/transformer/matching/PatternMatcher.java | 91 |
1 files changed, 54 insertions, 37 deletions
diff --git a/sources/scalac/transformer/matching/PatternMatcher.java b/sources/scalac/transformer/matching/PatternMatcher.java index d3e24a3c69..99a921e2e4 100644 --- a/sources/scalac/transformer/matching/PatternMatcher.java +++ b/sources/scalac/transformer/matching/PatternMatcher.java @@ -280,6 +280,22 @@ public class PatternMatcher extends PatternTool { protected PatternNode patternNode(Tree tree, Header header, CaseEnv env) { switch (tree) { + case Bind(Name name, Typed( Ident( Names.PATTERN_WILDCARD ), Tree tpe)): // little opt. for x@_:Type + if(header.type.isSubType(tpe.type)) { + PatternNode node = mk.DefaultPat(tree.pos, tpe.type); + env.newBoundVar( tree.symbol(), tree.type, header.selector ); + return node; + } else { + ConstrPat node = mk.ConstrPat(tree.pos, tpe.type); + env.newBoundVar( tree.symbol(), tree.type, gen.Ident(tree.pos, node.casted)); + return node; + } + case Bind(Name name, Ident( Names.PATTERN_WILDCARD )): // little opt. for x@_ + PatternNode node = mk.DefaultPat(tree.pos, header.type); + if ((env != null) && (tree.symbol() != defs.PATTERN_WILDCARD)) + env.newBoundVar(tree.symbol(),tree.type, header.selector); + return node; + case Bind(Name name, Tree pat): PatternNode node = patternNode(pat, header, env); if ((env != null) && (tree.symbol() != defs.PATTERN_WILDCARD)) @@ -287,43 +303,44 @@ public class PatternMatcher extends PatternTool { tree.type, header.selector); return node; - case Apply(Tree fn, Tree[] args): // pattern with args - if( isSeqApply((Apply) tree ) ) { - if ( !delegateSequenceMatching ) { - switch (args[0]) { - case Sequence(Tree[] ts): - return mk.SequencePat( tree.pos, tree.type, ts.length ); - } - } else { - PatternNode res = mk.ConstrPat(tree.pos, tree.type); - res.and = mk.Header(tree.pos, header.type, header.selector); - res.and.and = mk.SeqContainerPat( tree.pos, tree.type, args[ 0 ] ); - return res; - } - } - return mk.ConstrPat(tree.pos, tree.type); - case Typed(Ident ident, Tree tpe): // variable pattern - PatternNode node = - (header.type.isSubType(tpe.type)) ? - mk.DefaultPat(tree.pos, tpe.type) - : mk.ConstrPat(tree.pos, tpe.type); - if ((env != null) && (ident.symbol() != defs.PATTERN_WILDCARD)) - switch (node) { - case ConstrPat(Symbol casted): - env.newBoundVar( - ((Tree.Typed)tree).expr.symbol(), - tpe.type, - gen.Ident(tree.pos, casted)); - break; - default: - env.newBoundVar( - ((Tree.Typed)tree).expr.symbol(), - tpe.type, - header.selector); - } - return node; - case Ident(Name name): // pattern without args or variable - if (tree.symbol() == defs.PATTERN_WILDCARD) + case Apply(Tree fn, Tree[] args): // pattern with args + if( isSeqApply((Apply) tree ) ) { + if ( !delegateSequenceMatching ) { + switch (args[0]) { + case Sequence(Tree[] ts): + return mk.SequencePat( tree.pos, tree.type, ts.length ); + } + } else { + PatternNode res = mk.ConstrPat(tree.pos, tree.type); + res.and = mk.Header(tree.pos, header.type, header.selector); + res.and.and = mk.SeqContainerPat( tree.pos, tree.type, args[ 0 ] ); + return res; + } + } + return mk.ConstrPat(tree.pos, tree.type); + + case Typed(Ident ident, Tree tpe): // variable pattern + boolean doTest = header.type.isSubType(tpe.type); + PatternNode node = doTest ? + mk.DefaultPat(tree.pos, tpe.type) + : mk.ConstrPat(tree.pos, tpe.type); + if ((env != null) && (ident.symbol() != defs.PATTERN_WILDCARD)) + switch (node) { + case ConstrPat(Symbol casted): + env.newBoundVar( + ((Tree.Typed)tree).expr.symbol(), + tpe.type, + gen.Ident(tree.pos, casted)); + break; + default: + env.newBoundVar( + ((Tree.Typed)tree).expr.symbol(), + tpe.type, + doTest ? header.selector : gen.Ident(tree.pos, ((ConstrPat) node).casted)); + } + return node; + case Ident(Name name): // pattern without args or variable + if (tree.symbol() == defs.PATTERN_WILDCARD) return mk.DefaultPat(tree.pos, header.type); else if (tree.symbol().isPrimaryConstructor()) { assert false; // this may not happen ?? ----------------- Burak |