我正在编写一个表达式求值程序,它解析数学表达式并返回一个抽象语法树。我的树由运算符节点,数字节点和变量节点组成。这些中的每一个都实现了ASTNode接口,该接口需要实现getValue()方法。
我的第一个设计问题是运营商节点。我有一个抽象的运算符类,其中包含有关优先级的信息的字段,运算符是一元函数还是二元函数,以及运算符是否是正确关联的。这些字段是通过受保护的构造函数设置的。有一个抽象方法operate()允许客户端扩展运算符类并创建自己的运算符。我还有许多默认运算符,它们存储在静态DEFAULT_OPERATORS HashMap中。每个运算符节点都存储一个运算符和操作数,它们只是其他ASTNode。当在运算符节点上调用getValue()时,它获取其参数节点的值,然后使用其运算符定义的操作返回结果。每个运算符只能存在一次,因为几个不同的运算符节点可以指向同一个运算符,但我认为没有办法强制客户端维护它。例如,树中的加号节点应该共享加号运算符的相同实例。
这个问题有点复杂。变量节点只返回由客户端设置的变量值。我打算将变量的值存储在HashMap中,将名称映射到值。但是这个HashMap在哪里存储以及它如何与树相关联。变量节点是叶子,所有变量节点都需要访问HashMap,但必须从只能访问树根的客户端设置值。我需要一些方法让树中的每个节点都可以全局访问变量HashMap,而我宁愿避免为每个节点提供对映射的引用,并能够设置值。
答案 0 :(得分:0)
对于作为(或不是)单例实例的运算符,如果运算符实现没有状态,那么这不应该构成问题。如果他们确实拥有州,那么客户实施者的工作就是保证他们不会搞砸。我不确定你能在" API"上做些什么。端。
对于变量查找问题,您的evaluate
(或getValue
)方法应采用context
参数,这样可以查找变量值。这也允许您拥有设置变量的运算符。