aboutsummaryrefslogtreecommitdiff
path: root/compiler/ast.go
diff options
context:
space:
mode:
authorRyo Nihei <nihei.dev@gmail.com>2021-05-25 21:55:17 +0900
committerRyo Nihei <nihei.dev@gmail.com>2021-05-25 21:57:45 +0900
commit520bf02582be7ab36b17fd78f8931cfdb702b07f (patch)
treea1e7ad54915152fce6f96a18312e28f34f256c84 /compiler/ast.go
parentFix the initial state number (diff)
downloadtre-520bf02582be7ab36b17fd78f8931cfdb702b07f.tar.gz
tre-520bf02582be7ab36b17fd78f8931cfdb702b07f.tar.xz
Add fragment expression
A fragment entry is defined by an entry whose `fragment` field is `true`, and is referenced by a fragment expression (`\f{...}`).
Diffstat (limited to 'compiler/ast.go')
-rw-r--r--compiler/ast.go38
1 files changed, 38 insertions, 0 deletions
diff --git a/compiler/ast.go b/compiler/ast.go
index a419f98..7d3965a 100644
--- a/compiler/ast.go
+++ b/compiler/ast.go
@@ -19,6 +19,7 @@ var (
_ astNode = &concatNode{}
_ astNode = &altNode{}
_ astNode = &optionNode{}
+ _ astNode = &fragmentNode{}
)
type symbolNode struct {
@@ -306,6 +307,38 @@ func (n *optionNode) last() *symbolPositionSet {
return n.lastMemo
}
+type fragmentNode struct {
+ symbol string
+ left astNode
+}
+
+func newFragmentNode(symbol string, ast astNode) *fragmentNode {
+ return &fragmentNode{
+ symbol: symbol,
+ left: ast,
+ }
+}
+
+func (n *fragmentNode) String() string {
+ return fmt.Sprintf("{type: fragment, symbol: %v}", n.symbol)
+}
+
+func (n *fragmentNode) children() (astNode, astNode) {
+ return n.left, nil
+}
+
+func (n *fragmentNode) nullable() bool {
+ return n.left.nullable()
+}
+
+func (n *fragmentNode) first() *symbolPositionSet {
+ return n.left.first()
+}
+
+func (n *fragmentNode) last() *symbolPositionSet {
+ return n.left.last()
+}
+
func copyAST(src astNode) astNode {
switch n := src.(type) {
case *symbolNode:
@@ -320,6 +353,11 @@ func copyAST(src astNode) astNode {
return newRepeatNode(copyAST(n.left))
case *optionNode:
return newOptionNode(copyAST(n.left))
+ case *fragmentNode:
+ if n.left == nil {
+ return newFragmentNode(n.symbol, nil)
+ }
+ return newFragmentNode(n.symbol, copyAST(n.left))
}
panic(fmt.Errorf("copyAST cannot handle %T type; AST: %v", src, src))
}