【发布时间】:2020-02-16 21:26:17
【问题描述】:
在 AST 的特定实现中,我有一个 node,它是一个接口和 ExprNode、EvalNode 和一些叶节点。现在叶子节点可以是字符串节点或数字节点或函数节点
每个表达式节点只能有两个叶节点。一左一右。
type Node interface{
Pos() int64
Typ() NodeType
}
type StringNode struct{
Pos int64
Val string
Node
}
type NumberNode struct {
Pos int64
Val float64
Node
}
type ExprNode struct {
Lhs ??? //should accept either StringNode or NumberNode
Op Operation
Rhs ??? //should accept either StringNode or NumberNode
Node
}
type EvalNode struct{
Lhs *ExprNode
AllFlag bool
Rhs *ExprNode
Node
}
我想出了一个可能不是惯用的解决方法。我正在寻找是否有更好的方法来做到这一点
type LeafNode interface{
IsLeaf() bool
}
func (n *StringNode) IsLeaf() bool{
return true
}
func (n *NumberNode) IsLeaf() bool{
return true
}
type ExprNode struct {
Lhs LeafNode //workaround
Op Operation
Rhs LeafNode //workaround
Node
}
现在在上述解决方法中,IsLeaf() 函数对我来说没有意义,但我不得不使用它来限制 ExprNode 上接受的节点类型。
如果标题看起来过于宽泛,我们深表歉意。
问题:有没有更好的方法来编写上述场景。
注意:我只是在寻找处理上述场景的惯用方法,而不是寻找算法的替代实现。
【问题讨论】:
-
在这种情况下使用接口对我来说是惯用的。但界面本身并不完美。我不明白为什么
Lhs和Rhs不是Node类型。稍后您可以使用类型断言或类型开关来获取类型。 -
我会寻找一些叶节点共有的真正功能;如果没有,尝试为它们建立专用类型/接口似乎没有什么好处。
-
@Adrian 这样想:专用类型不是用于共享相同的特征(功能),而是用于共享相似的属性(字段)。就像可以在一组类型中通用的类型。
标签: go