算术表达式的中级改造——《C++沉思录》第8章

《算术表达式的初级构造》中的测试代码:

Binary_Node* t = new Binary_Node("*",
                     new Unary_Node("-", new Int_Node(5)),
                     new Binary_Node("+", new Int_Node(3), new Int_Node(4)))

对于这样的表达式,显而易见的问题是创建的节点无法释放,当然,用户可以逐一创建再逐一释放,但是原书作者认为不应该把内存管理这类烦心事推给用户,作者认为面向对象的抽象不够彻底,我们只是抽象出了表达式树的圆圈节点,没有对箭头建模,使得用户不得不亲自操作指针,这样,第7章的“句柄类”我们便可以拿来管理节点之间的指针。

把原来的Expr构造成句柄类,就解决了内存释放的问题,然后,添加显示计算结果的函数eval(),具体改造代码如下:

#include <iostream>
#include <conio.h>
#include <stdio.h>
#include <string>
using namespace std;
class Expr_Node;
//句柄类 class Expr {
friend ostream& operator<<(ostream&, const Expr&amp ;) ; Expr_Node* p; //节点指针 public: Expr(int); //创建一个Int_Node Expr(const string&, Expr); //创建一个Unary_Node Expr(const string&,Expr,Expr); //创建一个Binary_Node Expr(const Expr& t); Expr& operator=(const Expr&amp ;) ; int eval() const; void print(ostream&amp ;) const; ~Expr(); };
//节点 class Expr_Node{ friend class Expr; int use; protected: Expr_Node(): use(1){}; virtual void print(ostream&amp ;) const = 0; virtual ~Expr_Node(){}; virtual int eval() const = 0; };
ostream& operator << (ostream& o, const Expr& e) { e.print(o); return o; }
//无子节点的节点 class Int_Node: public Expr_Node{ friend class Expr; int n; public:
Int_Node(int k): n(k){}; void print(ostream& o)const{ o << n;}; int eval() const { return n;}; };
//一元节点 class Unary_Node: public Expr_Node{ friend class Expr; string op; Expr opnd;
public: Unary_Node(const string& a, Expr b) : op(a),opnd(b){}; void print(ostream& o) const {o << "(" << op << opnd << ")";}; int eval() const { if(op == "-") return -opnd.eval(); throw "error,bad op "+op+" Int Unary_Node"; }; };
//二元节点 class Binary_Node: public Expr_Node{ friend class Expr; string op; Expr left; Expr right; public: Binary_Node(const string& a, Expr b,Expr c) :o p(a),left(b),right(c){}; void print(ostream& o) const{o << "(" << left << op << right << ")";}; int eval() const { int op1 = left.eval(); int op2 = right.eval(); if(op == "+") return op1+op2; if(op == "-") return op1-op2; if(op == "*") return op1*op2; if(op == "/" && op2 != 0) return op1/op2; throw "error,bad op "+op+" Int Binary_Node"; } };
Expr::Expr(int n) { p = new Int_Node(n); };
Expr::Expr(const Expr& t) { p = t.p; ++p->use; };
Expr::Expr(const string& op, Expr t) { p = new Unary_Node(op, t); };
Expr::Expr(const string& op, Expr left, Expr right) { p = new Binary_Node(op, left,right); }
Expr& Expr: :o perator =(const Expr& rhs) { rhs.p->use++; if(--p->use == 0) delete p; p = rhs.p; return *this; }
int Expr::eval() const { return p->eval(); };
void Expr::print(ostream& o) const { p->print(o); };
Expr::~Expr() { if(--p->use == 0) delete p; }

类图如下:

《C++沉思录》第8章

测试代码:

Expr t = Expr("*",
              Expr("-", Expr(5)),
              Expr("+", Expr(3), Expr(4)));
cout << t << " = " << t.eval() << endl;
t = Expr("*",t,t);
cout << t << " = " << t.eval() << endl;
Posted in 编程, 读书 | Tagged , , | Leave a comment

美国人拍不了的电影

前天在迅雷瞄到了一部美国电影《守法公民》,看评论不错就一路看下来,故事前半段还不错,讲一个高智商男人向美国法律宣战,利用布局复仇的故事,斯巴达男人拥有了高智商,杀人于千里之外,这种斗智题材在美国电影中比较少见。

可是越往后看越不对味儿,导演本已经让主角克莱德站在法律的对立面与黑人律师斗法,本意是对司佳节又重阳法系统形成挑战,最后却死于黑人律师的布局里,10年的复仇准备,通往地道都挖的那么宽敞,竟然忘记抹去自己的房产记录,竟然没发现仓库的铁门是黑人律师用铁棒撬开的,这种白痴错误竟然发生在斗智影片里,故事收尾太草率了。

记得前些年美国翻拍《无间道》,莱昂帅哥表演再卖力,编剧不下功夫,仍然免不了沦为烂片,恐怖片据说是成本比较低的片种,就拿美版《午夜凶铃》来说,美国恐怖片从来脱离不了血浆和尸体,不知是不是为了社会责任感,买大量的番茄酱来拉动内需。

还是一位网友说的比较到位:“美国,从不知道有种力量是内在的。”

Posted in 电影 | Tagged , , | Leave a comment

算术表达式的初级构造——《C++沉思录》第8章

dghkjsk7_51hng64vc5_b

一棵算数表达式树:(-5)*(3+4),这棵树的节点类型包括:常数、一元运算符、二元运算符。
假设我们可以设计一个函数Expr(),可以完成一元和二元运算表达为Expr t = Expr("*",Expr("-",5), Expr("+",3,4)),但这种方法灵活性极差。
如此一来,我们可以利用面向对象,将这棵树分解为节点(圆圈)和边(箭头),节点的内容包括操作数和操作符,因此存在着三种节点:
1、包含着一个整数值,无子节点;
2、一元表达式;
3、二元表达式;
由此,所如下类定义——
#include <iostream>
#include <conio.h>
#include <stdio.h>
#include <string>
class Expr;
//节点 class Expr_Node{ friend ostream& operator <<(ostream&, const Expr_Node&amp ;) ; protected: virtual void print(ostream&amp ;) const = 0; virtual ~Expr_Node(){}; };
ostream& operator << (ostream& o, const Expr_Node& e) { e.print(o); return o; }
//无子节点的节点 class Int_Node: public Expr_Node{ friend class Expr; int n; public: Int_Node(int k): n(k){}; void print(ostream& o)const{ o << n;}; };
//一元节点 class Unary_Node: public Expr_Node{ friend class Expr; string op; Expr_Node* opnd; public: Unary_Node(const string& a, Expr_Node* b) : op(a),opnd(b){}; void print(ostream& o) const {o << "(" << op << * opnd << ")";}; };
//二元节点 class Binary_Node: public Expr_Node{ friend class Expr; string op; Expr_Node* left; Expr_Node* right; public: Binary_Node(const string& a, Expr_Node* b,Expr_Node* c) :o p(a),left(b),right(c){}; void print(ostream& o) const{o << "(" << *left << op << *right << ")";}; };
翻译成类图:
expr11
测试代码:
Binary_Node* t = new Binary_Node("*",
                new Unary_Node("-", new Int_Node(5)),
                new Binary_Node("+", new Int_Node(3), new Int_Node(4)));
        cout << *t << endl;
测试结果:
((-5)*(3+4))
Posted in 编程, 读书 | Tagged , | Leave a comment

德字辈的都很NB

一日,跟曲曲看NBA的体育新闻,看到霍华德的一个灌篮。

曲曲惊叹道:“这黑猩猩,真厉害!这是谁呀?”
我瞥了瞥了这个球盲,淡淡的说道:“魔兽——霍华德。”

一会儿,电视上出现了基德进球的画面。

曲曲又惊叹问道:“这小个子也很厉害呀,白人也不差嘛!”
我又淡淡说道:“这是基德,而且不要因为他站在一群巨人里面就以为他是小个子,他有1米93呢。”
曲曲哝哝道:“哦……是吗,又是个德呀!”

我突然心生恶半夜凉初透搞创意,转头对她说:“NBA里面,名字带德都很NB哦,呐,你看这个韦德、罗德曼、德克……”
我又指着电视说:“看!这个是詹姆斯”。

曲曲急忙说道:“名字没有德哦?”
我急中生智说道:“詹姆斯.邦德嘛!”

曲曲挥着小拳头,打在我的肩膀上:“你就跟我掰吧吭,007都出来了,我还朱德嘞!”
我忙说:“没错,听说朱德打篮球也不错!唷!看,科比.布莱恩德!”

Posted in 趣事 | Tagged | Leave a comment

读《无限恐怖》

最近没事情的时候,就会掏出手机翻看《无限恐怖》这部小说。

大体讲的是现世的人可通过电脑中的一个提示框进入一个恐怖片的冒险轮回,在完成一部片子提供的任务后,就会被传送到一个叫做主神空间的地方,在那里可以兑换各种道具提高自己的能力,甚至能造出自己心目中的人来,等待十天进入下一部恐怖片,如此轮回下去,故事讲述的就是以郑吒、楚轩为首的中洲队的冒险经历。

初看到简介时,感觉剧情蛮扯淡,欲弃之不读,却无意看到百度贴吧里有无数膜拜者,我也顿时有了兴趣,草草读来,果然人物、故事都描写的非常精彩。

故事中,主神从未露过面(我感觉也不会是主神广场上的光球),楚轩猜测主神是一段程序,而主神几乎是小说中最高的存在,因为任何传说中的物件都可以从主神那里兑换得到,人类的文明甚至神话都被它玩弄于股掌之间,主神可以随意操作剧情,大家小时候都玩弄过昆虫吧,像一只小蚂蚁爬过一颗石头,你就在他面前堆起一座小土丘,再爬过去,就让他爬上高出,然后吹一口气让他从高处落下来。

轮回小队在主神面前是蚂蚁一般的试验品,战斗漫长而残酷,一路危机重重,遇到的也都是比西游的唐三藏碰到的更变半夜凉初透态的怪物,一不留神便被杀掉,人类究竟通过战斗能进化到什么程度,似乎这是主神要验证的东西。

情节中的主神充当了现实中的历史的作用,人类的进化在漫漫时间长河中速度缓慢,主神让弱小的人类进入自己设计的世界,催化了他们的进化,终极人类究竟能进化到什么程度?想起了前些天看过的《守望者》这部电影里的曼哈顿博士,几乎跟神一样了,那能力真的是无限恐怖了。

人类,究竟有多少未开发的潜能,开发出来究竟是不是件好事呢?

读科幻小说,最喜欢这种仰望星空的感觉,茫茫星空,一望无际,让自己对无限的未知有所敬畏。

Posted in 读书 | Tagged , , | Leave a comment

无关乎教育

我现在住的地方,小区物业不好,楼比较破旧,楼道上几乎没有完整的窗户。

我楼下一楼的住户是母女俩开的一家少儿英语学习班,每天下午5点多下班回家,走到楼下,都会看到年轻些的女老师带着学生在楼前做英语游戏,楼前杂草丛生,一群孩子叽叽喳喳的倒不在乎,像念快板似的,有节奏的一问一答:

女老师:苹果是什么?
孩子们:苹果是Apple。
女老师:桔子是什么?
孩子们:桔子是Orange。
女老师:桃子是什么?
孩子们:……

孩子玩得兴起,接着,家长陆陆续续过来接孩子,女老师喊着孩子们的英文名字,一一向学生招手告别。

那天教师节,我在楼下看到每个小孩的手上拿了两枝花,看到英语班的女老师便围了上去,把手里的一枝花交给她,然后与女老师告别跟着家长上学去了,我才明白过来,原来现在教师节要送花呀。

当天,跟同事谈到这件事,我说我记得我上学那会儿,教师节没什么特别的,最多就是上课前集体起立时一起说句祝福的话。同事则说,现在送花算好的了,送钱的都有,送三千块钱很正常,我不禁哑然了。

Posted in 生活 | Tagged , , | 2 Comments

蔬菜家园保卫战——《植物大战僵尸》

这次,豌豆、坚果、辣椒、土豆、卷心菜这些蔬菜的舞台不是餐桌,而是你家的花园,他们也不是毫无话语权的食品,而是拿起自己特殊武器保卫你的家园的士兵,对手则是门外一群群如潮水般涌来的拥有各种特长的僵尸,他们的邪有暗香盈袖恶目的只有一个,就是你的脑子。

魔兽的塔御游戏跟这款PopCap的《植物大战僵尸》的游戏方式很像:收集阳光在花园里种植蔬菜,防御侵犯家园的僵尸。游戏的花样在于不同的蔬菜和僵尸拥有各自技能,每个关卡有限的蔬菜选择要取决于将要上场的僵尸的类型,还附带着许多小游戏,耐玩性极强,可不要指望一两天之内爆机。

Posted in 游戏 | Tagged , , | 8 Comments

上周赶个项目,疯狂的代码工作,估计一周就只睡了不到10个小时,累!

平时不怎么眷恋的床,突然变得对我有无比的吸引力,哪怕坐在上面都能感到浑身的细胞在打瞌睡,强烈的怀疑这世界上怎么会有失眠这种事情的发生。

由此想到,人果然是种需求性动物,缺少什么就会感觉到什么弥足珍贵。人这种群居性动物住在一起,形成了社会,也把彼此同化了,各自的需要也被极大的统一了,货币把人们的目标做了最根本的统一,为了这一目标有了合作也有了争执,如果人人都为了兴趣去玩艺术、玩技术,那必须是在至少温饱线之上的生活,像欧美的技术人员,可以抛开工作去搞开源、搞音乐,总之去搞兴趣,而国内我这个年龄的人,大部分有着另一个称呼——房奴、车奴、卡奴,何谓‘奴’,就是你必须为他们效劳,鞠躬尽瘁,死而后已,得围着他们打转转。

说到这儿,我也会想,美国人也不是真潇洒,而是今天花明天的钱,这不,一次次贷危机连明天的钱也没了,搞得好莱坞的摄影师都得翻山越岭到大峡谷去淘金,关键是人家花明天钱玩兴趣的时候心态好,人家觉得是应该的,我交税我有权享受福利,像我一个朋友说的那样——反正是银行的钱,那就花呗。

Posted in 生活 | Tagged , | Leave a comment

《17 again》——人生是一场没有存档的游戏

perry17again_5

本剧具有的几个梦幻元素:

  • 善良的帅锅难找,有运动天赋的善良帅锅更难找,想找专一的有运动天赋的善良帅锅则是难上加难,有责任心的有同情心的专一的有运动天赋的善良帅锅,则可以被当作地球灭绝动物关在笼子里供大家参观或者放在实验室里当标本搞研究了;
  • 情节老套的穿越剧情,中年男人穿越时空,回到威风八面的17岁高中生活,跟女儿、儿子做同学,同时重新获得了选择爱情和前途的机会,但主角仍然为了爱情甘做小小销售员,难道爱情和前途真的是鱼和熊掌吗;
  • 在美国写软件原来这么赚钱,主角的死党ned,写了一个音乐维权软件,又写了一个音乐盗版软件,这么个贼喊捉贼的软件作者,就可以住豪宅、买跑车、收藏着各种电影道具,整三台高档液晶同时Game,搞得人心里痒痒的,起码在国内这着实梦幻;
  • 遗传基因绝对是个靠不住的东西,老子是帅锅老婆是仙女,仍然可能有泰极否来的事情发生,不相信?看看主角的闺女和小子就知道啦。

梦幻归梦幻,笔者仍然力荐本剧,关键是导演把这几个梦幻之处把握的恰到好处:

  • 主角演员zac(名字记不清了,有待于考证)相当会演戏了,尤其在把握这么一个有成年人心里的17岁少年角色时,无论是面对问题少年,还是自己的爱人,都能演绎的很到位,可是帅锅脸在本剧中屡遭蹂躏,先是被自己的媳妇儿又揉又捏,然后被女儿的同学和ned吧唧吧唧的打,真是太惨了;
  • Matthew Perry绝对是个卖点,想想《老友记》中Chandler撇嘴的坏坏一笑,想不起来了?本剧片尾就有张他17岁的照片,哎~!人到中年真的很可怕呀(不行我得赶紧做俯卧撑);
  • ned是个出彩的人物,每个动作都绝对的搞,本剧不可缺少的笑料,他的事情可以单独拍一部大龄宅男的恋爱史诗式电影了;
  • 基因再没传下去也是自己的孩子呀,当Mike重返17岁,没有坚持走向自己辉煌的未来,看到自己的孩子深处困境时,仍然选择保护他们,选择了保护家庭,也就是坚持了当初对爱情的选择,这是最能体现出本片主题的部分。

记得《武林外传》有那么一集,几位主角幻想自己当初如果改变某个影响自己一生的选择,现在也不会怎样怎样了,或许我们自己有时回忆起自己来,想想如果过去那个时候不怎么样现在可能就会怎么样了,想想当初如果不浪费时间,现在可能会生活的更好,其实回到过去我们可能仍然虚度着些许光阴,仍然懒散的生活。

Posted in 电影 | Tagged , , | 1 Comment

仙剑——触动你心里那块最柔软的小肉肉

仙剑——触动你心里那块最柔软的小肉肉,所以请支持正版。

就算是硬汉,心里总有一块柔软的小肉肉(读yoyo,即yo2,^_^),当眼前一些事情的发生触及到它时,情绪就会在心里激起涟漪、掀起波澜,甚至如海啸般涌来。

仙剑,毫无疑问可以触碰到许多人心里的那块小肉肉,姚壮宪当初一次感情的失败经历形成了仙剑一,一首蝶恋让许多对情感刚刚懵懵懂懂的年轻人知道了对于感情应该怎样的执着,自己对于这款游戏的喜欢还在于对于民族文化的弘扬,随手搜一首仙剑3中的词便可见一斑:

宜男草·紫萱
  
  碧水连天静无浪
  转东风
  滟纹微涨
  个中趣
  莫遣人知
  年年日日
  兰舟共上
  
  平生书癖已均恙
  解名缰
  更逃羁网
  春近也
  梅柳频看
  花间闲度
  细雨流光

仙剑3拍了电视剧,看了几集,虽然人物的出场介绍像是网游CG,虽然景天被演成了小痞子(游戏中的景天可是很有礼貌的有为青年),虽然剧中出现了对讲机,但相比仙剑1的电视剧的瞎胡闹,终于可以看的下去了,剧中采用了不少游戏中的经典音乐,如果能出现游戏中的诗词则会更增加几分韵味。游戏翻拍影视成功的例子少之又少,想想金庸先生的作品,小说也是一样的,理解上的不同,加上换一种形式表达,差一点拥泵们便会觉得就差了很多,所以想要了解仙剑,还是玩游戏,其实玩RPG就是读小说,只是小说的情节的进程是由你的手来操控。

Posted in 电影 | Tagged | Leave a comment