《c++沉思录》--一个面向对象程序范例

面向对象有三个要素:

数据抽象,继承以及动态绑定

 

问题描述:

 

1、一个表达式树包括代表常量、一元运算符、二元运算符的结点。

2、我们希望通过调用合适的函数来创建这棵树,然后打印这棵树的完整括号化形式。

 

面向对象的解决方案:

我们可以用一个联合(UNION)来容纳具体的值,用一个List来表示子结点,以包含联合(UNION)和List的类来表示结点。这些类有一个共同点:每个类都要存储一个值以及一些子结点,当然也有不少不同点,比如它们存储的值的种类,子结点的数目,继承可以捕捉这些共同点,而动态绑定帮助各个结点知道它的身份。

进一步分析,我们发现这棵树有三种结点:

1、整数表达式,无子结点

2、包含一个一元表达式,有一个子结点。

3、包含一个二元表达式,有两个子结点。

 

我们需要一个类来表示结点的"概念",但这个类并不表示具体的结点。我们将这个公共基类命名为Expr_node:

class Expr_node

{

            //友元函数,重载<<操作符用于输出

            friend ostream operator<<(ostream&, const Expr_node&)

            {

                    

            }

protected:

            virtual void print(ostream& ) const = 0;

            virtual ~Expr_node() {};

}

因为所要创建的对象都派生至Expr_node,所以提供了虚析构函数。动态绑定只用于成员函数,所以我们定义了一个虚函数print。我们希望用户使用输出操作符,而不是Print函数,那么把Print设为Protected,把operator<<设为友元。

从函数Print的声明可以看出,它是一个纯虚函数,这就使得Expr_node成为抽象基类。这就体现了我们的意图:不存在所谓的Expr_node对象。Expr_node类的存在只是为了获得公共接口。

 

输出操作符:

ostream& oprator << (ostream & o, const Expr_node e)

{

            e.print(o);

            return o;

}

 

下面定义具体的类:

1、整数,无子结点的结点类

class Int_node:public Expr_node{

            friend class Expr;

            int n;

 

            Int_node(int k) : n(k) {}

            void print(ostream & o) const { o << n; }

}

 

2、一元结点类

class Unary_node: public Expr_node{

          //friend class Expr;  

          string op;

          Expr_node * opnd;

          Unary_node(const string & a, Expr_node * b):Op(a), opnd(b) {}

          void print(ostream & o) const

          {o << "(" << op << *opnd << ")";}

}

 

 

3、二元结点类

class Binary_node: public Expr_node{

          //friend class Expr;  

          string op;

          Expr_node * left;

          Expr_node * right;

          Binary_node(const string & a, Expr_node * b,Expr_node * c):Op(a), opnd(b),opnd(c) {}

          void print(ostream & o) const

          {o << "(" << *left << op << *right << ")";}

}

 

创建一元和二元表达式的构造函数期望获得指针,于是我们可以动态分配结点:

Binary_node * t = new Binary_node("*",

                              new Unary_node("-", new Int_node(5)),

                              new Binary_node("+",new Int_node(3), new Int_node(4)));                 

 

显然这里存在一个问题,我们不再拥有内部new的对象的指针了。下一节介绍如何new 和 delete对象。

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值