我想很多C++程序员应该有和我一样的感受,所以,兄弟们分享一下自己使用过的设计模式和使用场景吧,顺便说一下自己掌握了多少个设计模式及工作年限等,方便膜拜。呵呵
======================================================================
对于商业用的软件工程,追求时效是必然的,即使是很正规的公司,也要先卡时间。当然这样的公司,也许后面会给一段时间再完善。但这个时代毕竟这样的公司不多。大多都是应付客户而已,完成功能即可,但这样对公司的技术储备和经验积累都不利,也对个人编程能力的发展不利。
我觉得,你的想法非常好,能把问题抽象出来看,才会做得更完美,也看得更远,自己的视野也会更开拓。那么就在应付完项目后,如果有时间整理一下自己的工作,按自己的想法再加工一下。如果公司有软件更新的下一个版本的话,你就会用到这个。这样做出的软件更易于维护和发展。即使没有下一个版本,这样的总结和积累,也是一个对自己能力发展的促进。呵呵,当然也会有成就感。
======================================================================
一般都是先会编程、写项目,然后才去学习设计模式
能用设计模式去规划项目的并不多
设计模式是从实际开发中提炼出来的,实际上你在做开发时已经在自觉或不自觉的在使用“设计模式”
不信你把你的项目撸一撸,看看都是哪些设计模式的应用
======================================================================
是这样的,个人感觉很多C++的到了工作的第2.5年之后才会用,而且用的不标准,甚至混乱,导致代码不清晰,难维护,如果一开始就能掌握理论,接着学着使用就更好了,就像学会了加减乘除再去菜场买菜一样。
所以开个帖子,希望大家受益,讨论。
大家还是说说自己用过的场景吧。
======================================================================
从底层设计起来的大的工程才需要设计模式吧,毕竟用设计模式还不如用一个框架,android这种的基本上是告别设计模式了。其实编多了之后,自然就有些概念性思想,这些思想其实跟这些设计模式差不多。就像Android中,用单例的情况还是比较多的,但算不上是一个设计模式,小技巧而已。存指针和引用的方式应该也是惯用,但也算不上一个标准的观察者模式。
实习的时候,公司有一个从底层建起来的项目,我接触到的大概150w行代码,一些更底层的库我没权限看代码。
用的就是全局的观察者模式,目的就是在任何一个类里的任何一个函数内都可以操纵所有的类和函数,使用起来非常方便,可以在任意的地方加任意的功能。更妙的是利用com接口的一些特性,可以根据类本身,获取一个com基类,再用这个基类加uuid就可以访问所有。
======================================================================
在这一年多的工作中也感觉到很多时候一个项目下来基本没什么时间让你去设计,只有让你想想怎么实现功能的时间。看了设计模式的书,也发觉很多时候用不上,最多也就是简单的单例、工厂、策略模式等。刚开始学的时候,老是在想这个设计模式能不能用,要怎么用,特别是想不出来时,真的挺让人郁闷的。后来也不这样做了,只记得了设计模式的本质,封装变化、抽象编程。后来编写代码的时候也就想想哪个地方是会变化的,需要抽取出来,能不能自己简单的抽象下处理,不行再去看看有没有解决类似问题的设计模式吧,个人愚见,哈哈
======================================================================
我博客中有些关于设计模式的文章,可以参考下:
http://www.cppblog.com/weiym/archive/2012/06/10/178319.html
http://www.cppblog.com/weiym/archive/2012/06/12/178472.html
关于怎么学习设计模式:
1. 把GOF的设计模式看3遍以上,看懂为止
2. 看优秀开源代码,看别人是怎么使用设计模式的
3. 自己尝试实践和运用模式
C++ 支持多种范型,因此设计模式在C++使用不是很典型,纯面向对象语言,如java和C#,它们在设计模式使用上往往更彻底。
http://www.cppblog.com/weiym/archive/2013/04/27/199781.html
上面有人提到
“实习的时候,公司有一个从底层建起来的项目,我接触到的大概150w行代码,一些更底层的库我没权限看代码。用的就是全局的观察者模式,目的就是在任何一个类里的任何一个函数内都可以操纵所有的类和函数,使用起来非常方便,可以在任意的地方加任意的功能。更妙的是利用com接口的一些特性,可以根据类本身,获取一个com基类,再用这个基类加uuid就可以访问所有。”
个人不是很同意, 大型程序各个类可以随意相互访问,是什么一种情况?即使基于COM接口,也是一坨乱麻。
大型程序首先强调模块化,模块以独立接口的形式暴露给外部, 各模块单向依赖, 一层层往上搭。COM本身是个好东西 ,但是以COM接口的名义将所有功能耦合在一起,随意QueryInterface,随意调用就不对了, 这样的网状依赖可能你暂时自己用的爽了 ,但是以后会让程序很维护, 模块很难重用,不符合软件工程低耦合高内聚的原则。
======================================================================
后来编写代码的时候也就想想哪个地方是会变化的,需要抽取出来,能不能自己简单的抽象下处理,不行再去看看有没有解决类似问题的设计模式吧
这个,我周末的时候刚刚想通了,呵呵,多谢。还是要抽些时间多学习一些,理论水平先上去,然后再在应用中发挥,不过那些理论学习的时候很枯燥,找不到有这些应用的代码,有的话一看就明白了。
======================================================================
什么是设计模式? 所谓设计模式就是前人在解决问题中总结的定式,如同解题公式,
没有设计模式一样实现代码,但当解决同样的问题时,要走别人走过的弯路。
学习设计模式就是学习一些思路,生搬硬套是要不得的。
我觉得设计模式像极了咱们老祖宗传下来的中国功夫,可能就是简单的二十四式,
招式需烂熟与胸,实战时,一切都是自然流露,不会特意去想用哪一招,完全根据场景,
对手、目标而自然的出招。而且需要变通和演化。
如果说你的代码中没有用到模式,那可能实战就是泼妇打架,一通乱拳了。高手当然不会
如此。
学习模式的一个捷径是看一些经典成熟的代码,MFC1.0诞生于1991年,你去看源代码和实例
会发现那里面已经用过很多模式了,其他高手代码一样如此。绝对不限于书上那一点点。
======================================================================
以后再做设计,坚决考虑可维护性。顶住压力,多运用设计模式,不会也要依葫芦画瓢,挨骂就挨骂吧,大不了自己多加点班。
那么到现在总结一下吧.
如何学好设计模式:
1.先具备理论素质,多看书,一定要用代码实现各种模式,哪怕是简单的例子(本人正在进行中,以资鼓励大家进行)
2.在项目中先将问题抽象,然后分析对应哪种模式,先套用,再修改完善。
======================================================================
推荐个学习设计模式的优秀代码资源: Delphi 中采用的VCL库,
这个库是使用Obejct Pascal写的,非C++,但设计模式其实在OO语言中是通用的,
VCL是个设计的非常不错的框架,是一个宝库,一般人我不告诉他
,内含很多优秀的设计模式,书上有的书上没有的都有。我做项目时经常参考并获益匪浅。。。
MFC没有VCL优秀,但用模式的地方也很多,看这个源码也可以。
因为设计模式的应用更多的是框架而非具体问题,所以一般应用最多的就是框架类库。
基本上优秀的框架中都有应用。
======================================================================
当你对自己的代码不断优化,重构,复用,心里想着如果别人用起来要易用,要可读性好,当你改到你可能改不下去的情况,忽然发现,卧槽这不是和XXX设计模式很相似!这时候你会充满极大的成就感。——设计模式本就是实践过程中总结出來的。
======================================================================
个人觉得设计模式注重的是以抽象的方式解耦合,能对抽象和耦合了解的比较深刻也绝非一日之功。建议先学习面向对象的基本思想,经常站在对象的角度思考问题。买几本书,建议先看《敏捷软件开发》,然后在看《设计模式》,后者虽然经典,但是论述比较学术化,初学者看这本书会比较困难。我在工作中用设计模式相当频繁,其实设计模式也绝非23种经典模式,它们可以交叉使用相互组合,只要你愿意,也可以创建自己的模式,前提是真的了解抽象和耦合问题。
======================================================================
设计模式什么的,也曾经研究过,但是看过就忘了,曾经自己做过一个项目,最初设计的时候想把设计模式加进去,但是想来想去,想的头都疼了,最后也没加进去。
个人觉得,面向对象,最主要的还是抽象这块,怎么把实际问题用面向对象的思想抽象出来,至于设计模式,只是提供的一种捷径而已。
但是现实项目中,由于时间的关系,很难有时间静下心来去抽象去设计,所以用模式的时候很少,也曾经想过把自己的编写过的代码重新在整理一下,抽象封装一下,让自己的代码更漂亮一些。
但是一想到要修改的地方太多了,就懒得弄了,最后就变成只要功能实现了就可以了。所以觉得自己的编程能力始终不上不下的,总感觉差那临门一脚,真正想要踢出去的时候,又发现不知道门在哪,所以很是困惑。
至于说到大的项目还是小的项目用到设计模式,我觉得其实都一样,都会用到,最主要的还是看抽象这块。
======================================================================
从来不去刻意套什么设计模式,目标只有一个,就是最大可能地重用代码,降低耦合。感觉首要是想好线程模型和状态机,确定实体的分层,然后在event loop内部适度地去抽象,怎么灵活怎么来,不必拘泥于这工厂那Builder的。曾经见过“学院派”同事写的代码,外表看一溜的设计模式化的命名和接口,倍儿花哨,里面却一团乱麻,一坨坨的if-else嵌套,外加几层的try-catch,还挂了好几把同步锁。心想这是何苦呢?当初设计过度,后来没空重构,烂代码像野草生长在被荒废的假山假庭院。如果忘记模式,自然地写,里面的逻辑也不至于这么绕。
======================================================================
OOP是一种思想,思想的实践依赖每个人的理解,所以很难说你在实际项目是否OOP了
设计模式,虽好但是却要根据实际的需求和项目结构来走的
目前主要从事NET平台开发的,所以这两快相对用的比较多点,用过部分C++也看过公司一些C++工程的代码,感觉好像设计模式和OOP思想的都很少在代码中得到体现~
在国内的中小公司更多的是追求进度而不是程序的结构和设计,也不会太多的考虑到以后的扩展和维护,所以在中小公司话说真的这两个东西见的太少了,甚至有些跟我同事的,都工作几年了,连设计模式都不知是为何物呢
======================================================================
以前搞c++还注意下,
现在搞c#,代码写了就用,无所谓模式,多理解oo的本质,关注下bad smell是不是太多就行了。
其实那些设计模式都是根据一些编程规范为c/c++量身打造的。
而在后一代的语法中,其实很多已经被集成进了语法特性中。
迭代什么的就不说了。
就一个泛型委托,就可以废掉多少设计模式?
其实我更觉得应该从反模式的角度去规范自己的代码。
大家可以看看反模式的一些定义,看有没有中枪。
以下摘录自百度百科,(然后百度貌似抄的维基)
基本概述
反模式(英文:Anti-patterns或pitfalls), 是指用来解决问题的带有共同性的不良方法。它们已经经过研究并分类,以防止日后重蹈覆辙,并能在研发尚未投产的系统时辨认出来。
软件开发中公认的反模式
编辑本段
项目管理
水中望月(Smoke and mirrors):向人演示还没有实现的功能看上去会是什么样的。英文缘自一项魔术手法:放出烟雾并趁机用镜子遮住一件物体,使它看起来像是消失了。
软件膨胀:随着版本的升级,软件越来越消耗系统资源。
不良管理︰在未对主题有足够认识的情况下管理一个专案。
编辑本段
设计反模式
反抽象:需要的功能并不暴露给用户,导致用户要在较高层次重新实现一些功能。
四不像:往往一个设计模型可以暴露不同的接口给用户,不同的接口表现了模型的不同方面。然而把不同方面的功能混在一起是常见的不良设计。
乱麻球:系统没有可辨认的结构,就像一团乱麻一样。
万应灵:一个对象了解的东西太多,或者要做太多的事情,就好像无所不能一样。
屠龙术:没有必要的复杂设计。
竞争危害(Race Hazard): 缺乏预见事件以不同顺序发生的后果。
面向对象设计上的反模式
万能类︰在一个类的设计中,聚集了太多的函数。
吵闹鬼︰建立某对象的目的只是为了传送讯息给其它的物件。
溜溜问题︰因结构(例如继承)极度破碎冗长,而必须花费极大力气来了解它。
编辑本段
编程反模式
硬编码(Hard Code):或称写死。在实现某系统用途上设死该系统的运作环境。
紊乱代码︰几乎无法理解的结构,特别是因为代码结构的滥用。
超布尔逻辑︰不必要的比较,或是过于抽象的布尔计算。
无用的例外处理︰插入了条件去防止运行时异常,但确在条件为false时又throw(例如:if A not null then process (A) else throw null-exception endif).
编辑本段
方法反模式
剪贴编程(Copy-n-paste programming):宁愿拷贝(并修改)现存代码而非创造通用的解决方案。
反重构: "移除功能性并以注解取代"的过程。
金锤子: 假设个人偏好的解决方案是世界通用。
掩耳盗铃: 假设一个已知的bug不会出现。
不成熟的优化: 根据不足信息优化。
重新造个轮子: 拒绝采纳现有的解决方案,重写一个。
造了个正方形的轮子: 当一个优秀的方案存在时,创造一个蹩脚解决方案。