1 module gamma.parsgen.lalr1.LRItem; 2 3 import gamma.grammar.Alternative; 4 import gamma.grammar.Symbol; 5 import gamma.grammar.SymbolNode; 6 import gamma.util.Indexed; 7 8 class LRItem : Indexed 9 { 10 const size_t index_; 11 12 Alternative alt; 13 14 const bool altIsInContinuationGrammar; 15 16 const size_t dotPos; 17 18 const bool complete; 19 20 Symbol symbolBehindDot; 21 22 Symbol symbolPrecedingDot; 23 24 LRItem nextItem; 25 26 this(size_t index, Alternative alt, bool altIsInContinuationGrammar, size_t dotPos, LRItem nextItem) 27 { 28 this.index_ = index; 29 this.alt = alt; 30 this.altIsInContinuationGrammar = altIsInContinuationGrammar; 31 this.dotPos = dotPos; 32 this.complete = (dotPos == alt.rhs.length); 33 34 if (!this.complete) 35 this.symbolBehindDot = (cast(SymbolNode) alt.rhs[dotPos]).symbol; 36 37 if (dotPos > 0) 38 this.symbolPrecedingDot = (cast(SymbolNode) alt.rhs[dotPos - 1]).symbol; 39 40 this.nextItem = nextItem; 41 } 42 43 public override string toString() 44 { 45 import std.array : appender; 46 47 auto writer = appender!string; 48 49 writer.put(this.alt.lhs.symbol.toString); 50 if (this.altIsInContinuationGrammar) 51 writer.put(" =>"); 52 else 53 writer.put(" ->"); 54 foreach (i; 0 .. this.dotPos) 55 { 56 writer.put(' '); 57 writer.put((cast(SymbolNode) this.alt.rhs[i]).symbol.toString); 58 } 59 writer.put(" ."); 60 foreach (i; this.dotPos .. this.alt.rhs.length) 61 { 62 writer.put(' '); 63 writer.put((cast(SymbolNode) this.alt.rhs[i]).symbol.toString); 64 } 65 return writer[]; 66 } 67 68 /** 69 * @see gamma.util.Indexed#index() 70 */ 71 public size_t index() const 72 { 73 return this.index_; 74 } 75 }