GP与OO,欢迎讨论。

cber 2001-09-26 10:11:52
故事起源于左轻侯兄写的一篇《泛型编程在非C++语言中的实现之探讨》(http://www.csdn.net/develop/article/10/10694.shtm),在文章后面,我和另外几位大虾就此发表了各自的看法(我会把它们都列在下面的),结果也没有得到一个明确的结论。因此我把它们转贴过来,希望能够有高手参与讨论,好让我与大家都能够对此有一个清晰的认识。

看法是逆序存在的,因此可能会比较难看:(

jasonk ( 2001-9-25 15:34:13 )

从应用角度上,我觉得OO贴近系统构造,它一般都会支持一种对象模型,所以能够在运行状态下访问对象接口,并且有一定的继承层次.比如COM中的IDispatch,CORBA重的Object,Servant_Base.而GP更加贴近上层的程序员,它的彼此之间的联系比较松散,本质上也没有对象的概念.

cber ( 2001-9-25 11:58:28 )

我不同意lynxliu的说法,GP绝对不能说是OO的延伸。
之所以有Procedure-Based, Object-Based, Obeject-Oriented, Generic Programming等program paradigms,都是为了使软件开发更容易管理,使软件开发方式更好的符合人们的思维习惯。
平心而论,GP是一种相对来说很新的paradigm,所以还有很多人无法领悟其中的精髓(我也不敢说自己就已经领悟了),但要说它是OO的延伸,我是肯定不认同的。我比较赞同的观点是:COM/CORBA等面向组件的开发可以算是OO的延伸。

lynxliu ( 2001-9-25 10:18:08 )

文章里面所举的例子我感觉两类语言各有特色。GP是一次编程思想的革命,我觉得很奇怪。我认为,他只是OO思想的一个延伸。核心实际上是为了绕过强类型语言的数据类型检查!(这一点上VB做的更简单,因为没有类型声明与检查)。所以,谈不上什么更大的意义,只是在代码的集中控制和重用方面,有好处。(还不如不使用强类型语言)其他机制,在这两点上确实,比不上类模板实现。但是,类模板不是必须的,OO推荐的正式方式是使用工厂类,而不是静态的类继承,多态机制。我在写一本有关的书,里面对这个问题,是这么解释的,不知道大家怎么看。

cber ( 2001-9-25 9:24:50 )

Austern98这本书没有电子版,不过SGI上面的STL文档就是它的原始材料,应该可以说是等于它的70%多。你可以去上面找来看看,而且它还是免费的。

qinghou ( 2001-9-24 23:55:45 )

鼓掌鼓掌,精彩纷呈:-)
有几个朋友都同时指出,类型安全性是这种思路中的一个大问题
“这些Concept中很多requirement用operator overloading作会很方便,这应该算是C++的特色吧”
这话比较中肯:-)
这也等于说,从理论上来说,用函数实现requirement也没问题的
我现在的认识是,用这种思路实现GP,基本上是可以的,但是确实远不如C++方便
cber兄,《Generic Programming and STL》这本书有没有电子版可供下载?我没有见过比较好的讲GP的书

passos ( 2001-9-24 21:57:06 )

我们也知道GP对于代码复用来说是非常有用的。
那么我们可以撇开C++的GP实现不说,是否有可能利用Delphi自身的条件来
实现GP所能够达到的效果呢?
毕竟我们不是要用Delpi重新写一遍C++的STL啊。
我想关注一下实际的效果应该还是有实际意义的。

cber ( 2001-9-24 17:03:43 )

GP是一种新的programming paradigm,和OOP基本上不搭界。根据Matt Austern在《Generic Programming and STL》中的见解,GP最核心的应该是Generic,表现为一堆的Concept组成的Hierarchy,其地位对应于OO中的Class Hierarchy。因此,要想彻底掌握GP,最好能够先将OOP抛一边,转而理解它独有的Concept Hierarchy中的精髓,然后再试图去理解这些Concept的实现。
STL中的algorithms中并没有强制要求要有operator overloading,它只是对每个algorithm有着一些Concept上面的要求,只要实作中参与该algorithm的元素(如sequence,element,iterator等)能够符合这些Concept的话,就认为该算法的实作品是一个合格的实作,而这些Concept中很多requirement用operator overloading作会很方便,这应该算是C++的特色吧^_^
我说单根继承的Serialization是强项,因为是它比较容易实现。而如C++式的继承方式,你将不得不对每个继承体系都来一次Serialization的实作,这是很烦人的(虽然它确实很符合我们的思维习惯)。
个人认为,要想学习好GP,可以看一部分有关哲学方面的书籍,可能会更好点。例如,我对于GP和OO的理解就是:OO体现了世界是由物体组成的;而GP则体现了世界是运动着的世界,我们应该透过各种不同的运动的表面去抓住它们的本质(也就是Generic)^_^

smartkid ( 2001-9-24 15:29:00 )

再说两句:

1)GP从其本质来说是算法与数据的分离,在面向对象语言中,它一般通过将一系列抽象的算法类来完成,并同时定义了算法类所处理的数据类。从这个角度上来说,它并不一定要利用模板才能实现。
2)模板的本身是对类的处理,而不是对对象的处理。所以模板为GP的实现提供了最佳的支持。
3)单根继承的Serialization比较容易实现,多重继承的Serialization更体现了面向对象的本意。这个话题其实说深了就是多重继承是否合适的问题,不仅限于Serialization。多重继承我认为要比单根继承更加合理,只是由于多重继承往往不容易被使用者掌握,所以很多面向对象语言都采用了单根继承。
4)Delphi的RTTI功能是不错,但RTTI和GP完全是两回事,不存在谁能替代谁的问题。
5)运算符重载和GP也是两回事。GP可以重载运算符来实现,也完全可以通过函数重载来实现。其实运算符重载并不能实现比函数重载更多的功能,它的作用只是让程序看起来显得“似乎”简单些。
6)Delphi完全可以实现GP,只是它的实现不如C++的实现好用:-)。要完整地实现GP,我觉得有至少要能够实现模板,对于多重继承勉强可以通过接口或对象组合来部分地模拟。

smartkid ( 2001-9-24 15:01:27 )

左兄鉴:

C++模板有两个在Delphi/Java体系结构中无法实现的优势:
1)避免了运行时动态类型转换的开销
2)编译阶段的类型检查
在Delphi/Java的实现中,如果想实现静态的成员类型检测必须通过从TStack继承或组合TStack来完成。

对Delphi有一个比较好的STL的实现,是个开放源码的项目: http://sourceforge.net/projects/decal/

smartkid@nari-china.com


qinghou ( 2001-9-24 13:23:58 )

说明一下:
我对很多东西的理解都没有把握,写下本文的目的完全是抛砖引玉,希望能够看到精彩的回复,增长自己的水平。发在几个坛子之后,回复比较踊跃,但是显然大家也分歧很大,众说纷坛,有的完全相反。而各位高手的发言又往往是点到为止,没有深入,让我这样的人看了更增疑惑。比如,有人认为模板是GP的必要条件,有人却认为模板跟GP毫无关系;cber认为serialize是单根结构的强项,但在大富翁上有人却认为C++中通过多重继承来实现serialize要远为灵活轻便……
能否请发言的高手多花一些时间,来充分阐明自己的观点?例如wao兄,你说的“非常强大的动态类型”是指什么?为什么有了它就不需要GP了呢?cber兄,你认为algorithm的实现必须使用运算符重载吗?如果Delphi/Java中增加运算符重载,是否就可以完整地实现GP呢?……
如果这个贴子能引起一场讨论,则我辈幸甚。
最后重复一句:“我的目的也不是一定要让Delphi/Java来跑GP,而是想探讨一下GP这种思想以另外一种思路实现的可能性。”我们当然不可能改变Delphi/java的语法,但可以讨论一下应该怎样改变语法,才能以另一种思路实现GP。这种纯理论的探讨也是很有意思的啊。

qinghou ( 2001-9-24 12:13:56 )

谢谢,我去找找DeCAL看
各位能推荐一些关于GP的专门书籍么?一般的C++资料说得都不详细

wao ( 2001-9-24 9:09:23 )

Java/Ojbect Pascal 是不需要GP的。因为他们有非常强大动态类型,并且效率根本就不是这种语言的出发点。例如smalltalk压根就没有静态类型,全部是运行时再确认的。

kundeng ( 2001-9-24 9:01:24 )

左大侠对号称Delphi STL的DeCAL库有什么看法?
我在SOurceforge上看到了这个库,早早下载了,但是却没有时间看,希望左大侠给我们吹一吹。
如果您没有DeCAL库,可以在http://sourceforge.net用关键字“Delphi STL”搜索到。

cber ( 2001-9-24 1:25:21 )

看完你的做法,感觉和MFC中的Collection Classes差不多。我认为,把所有的类都继承自同一个base是一个很蹩脚的做法:)还有,你在这篇文章中还没有讲如何实作GP中的另一个重要组成部分:algorithm,而在实作slgorithm时恰恰大量使用了操作符重载,这不能不说是现今的Delphi/Java的遗憾了。不过C++中现有的STL也不是很完美,至少它还不能实现serialize,这恰好是同一祖先的强项:(

我也比较赞同myan的说法:“每种语言都有最擅长的特点,不必非要以己之短,搏彼之长”。要知道,强扭的瓜通常都是不甜的,要真的想在Delphi/Java中实现完全的GP,还是等到它们支持足够多的必需语法再说吧。

bonly ( 2001-9-23 22:20:00 )

始终还是C++的优秀!!!

cber ( 2001-9-23 22:13:32 )

先做个标记,回头好好看看再说。

qinghou ( 2001-9-23 13:06:59 )

可能是我对GP的了解不对吧
我的印象中,GP主要就是将数据类型和通用算法独立起来的一种思想,从而可以在更高的层次上实现代码复用
至于实现是静态还是动态,似乎不是GP的特性吧?
能否说一说您对GP的理解?
我的目的也不是一定要让Delphi/Java来跑GP,而是想探讨一下GP这种思想以另外一种思路实现的可能性。这样可以加深我们对GP、对C++、对Delphi/Java的理解。

babysloth ( 2001-9-22 23:26:41 )

感觉左大侠的说法不对。
C++的GP是静态的,GP的效率与抽象并重。
您所说的是动态的,不算GP。
Java在OO上出色,GP却不行,何必强求老虎爬树呢?

qinghou ( 2001-9-22 19:46:15 )

我明白你的意思
Delphi/Java中对GP的实现,与C++对GP的实现是完全不同的两种思路,因此在template编程这个层次,根本不具有可比性,也不存在谁跑在前面的问题。但我关注的不是这个,而是GP本身。GP的思想本身,应该与语言是无关的。所以我也不同意“以己之短,搏彼之长”的说法。
“Object Pascal/Java/C#在面向对象和面向组件领域,较之C++有着明显的优势”,你指的是哪一方面?

myan ( 2001-9-22 18:53:28 )

你所使用的这种GP实现技术,基本上就是Smalltalk/Java中已经应用的泛型技术。当然不能说不是GP,但是跟C++的GP实在太不相同了。后者实际上是一种静态多态性技术,基于编译时的运算,大量运用template技术,以至于形成了所谓template metaprogramming风格。这方面,现在只有C++语言远远地跑在前面,包括Java打算引入的泛型机制,也远远没有达到今天C++的层次。

每种语言都有最擅长的特点,不必非要以己之短,搏彼之长。Object Pascal/Java/C#在面向对象和面向组件领域,较之C++有着明显的优势,好好地发挥这种长处吧!

...全文
2437 124 打赏 收藏 转发到动态 举报
AI 作业
写回复
用AI写文章
124 条回复
切换为时间正序
请发表友善的回复…
发表回复
linning2570 2001-12-28
  • 打赏
  • 举报
回复
┬┴┬┌─ ●─┬─  │─┼─┐ ●├─┤○
┴┬┴├┬ ┌─┼─ │◎ │ │ ○└┬┘●
─┼─││ │ │  ││─┴─┴ ──┼──
●│○││ ┴─┼─  │○  ● / │ \
lynxliu 2001-12-28
  • 打赏
  • 举报
回复
把GP推崇到如此地地位,恐怕是C++的特色。实际上,GP的产生我感觉和C的思想有关。C里面的宏代换,在C++里面演化为类模板。都是设计期的代码自动生成机制。相比之下,纯的OO运行时刻类型检查和转换,效率要低一些,但是没什么不可以。特别是使用动态模式,工厂类的方法以后,我认为Gp带来地好处主要是直观、简洁的表达,代码的集中控制。是否使用,和设计有关,个人还是很喜欢这个机制,希望Java早日加入支持。但是说道革命性的思想变化,也未见得,我宁愿看作是结构化思想在OO上面的借尸还魂,呵呵。说白了,可以绕过类型检查,统一操作,其实就是指针的类型转换而已。我喜欢vb,没有什么检查,更容易实现gp,c++的指针也可以,不那么安全。
tiongkohlang 2001-10-04
  • 打赏
  • 举报
回复
大家还是好好编程序吧。讨论这些东西其实没有什么实际意义。起码没有什么现实的意义。
讨论这些东西应该属于用哲学的精神来讨论问题,是一种纯理论的对真理的探讨,并不涉及什么实用性。我觉得大家的主要任务是积累经验,多多挣钱,所以不必花这么多时间在这种东西上。
askbill 2001-10-04
  • 打赏
  • 举报
回复
The STL is not merely a collection of containers and algorithms, but a conceptual framework for fundamental algorithms and data structures. Extensibility has always been a central design goal of the STL. The SGI Standard Template Library is a crucial first step toward this goal, and serves as a model for extending the STL. But there are still entire categories of fundamental algorithms that have not yet been addressed. Some of the most important omissions are graph algorithms, pattern matching, multidimensional data structures, and persistence.

SGI will continue to extend and enhance the STL, and will serve as a clearinghouse for suitable components that others wish to contribute. The STL will not merely be a static body of code, but will be a growing collection of efficient and interoperable software components.
hahaha88 2001-10-04
  • 打赏
  • 举报
回复
把不同型号/厂家/价格的声卡,通过同样的PCI接口,插进主板里,这是OO吧

红烧大象/黄焖长颈鹿/清蒸鲨鱼。。。“肠胃(通过封装不同的消化酶)”都能“消化”他们,
这是不是GP?

好香啊!哈哈哈哈哈

OO和GP看问题的角度好象不是完全相同。。。嘻嘻(砖头来了,哈哈哈哈哈)
askbill 2001-10-04
  • 打赏
  • 举报
回复
What do I have do design in a generic program in contrast to an object-oriented program? Can I use object-oriented design methods for modeling a generic program? Well, not really ....
First, not all elements of your generic program are classes. Algorithms for instance play an important role in generic programming, and they are function templates, not classes. If you want to reflect the existence of algorithms, you can be happy if your design method allows free code, as the Booch method does. In some design methods you will not even be able to express function templates in an appropriate way.
Secondly, classes in generic programming are mostly unrelated. There is no inheritance among containers, iterators, or algorithms. There are only few containment relationships among containers, iterators, and algorithms. It's true, containers have an allocator , and associative containers have a comparitor. However, the main classes do not contain each other
Also, class interfaces do not reflect all operations of a generic component. Take the interface of a vector for instance; you will notice that a vector provides iterators. But it is not obvious that you are allowed to use these iterators in a call to a sort-algorithm. Still, it is a property of a vector that it can be sorted via the sort-algorithm. More generally, you cannot see which operations (or algorithms) are applicable to a certain container. In an object-oriented program the sort-algorithm would most likely be a member function of the vector class. Hence the relationship between the container and the algorithm would be visible and could be expressed by means of an object-oriented design method. Since in generic programming many relationships are expressed in terms of implicit requirements to template arguments there is no way of modeling the relationships between elements in a generic program by means of an object-oriented design method.
In sum, object-oriented design is not ideal for generic programming. This does not really come as a surprise because object-oriented design methods essentially capture the semantics of object-oriented programming; that's what they are for.

to KKDogInBJ(KK_Dog): sorry :)
KKDogInBJ 2001-10-04
  • 打赏
  • 举报
回复
就我的理解,GP的核心思想在于将算法和数据的分离。建立在这个理解上,我的本意是,GP的成功在于它做到了这一点(至于它是用模版还是木板做到的这儿我们就不关心了),而这种思想并不是什么新东西,只不过将OO的思想发挥到了极至,所以,我不认为它是一种思想上的革命。
The STL is not merely a collection of containers and algorithms,这我也不同意,我甚至敢把STL换成Program说 Program is just a collection of Data and algorithms。
世界的本元是什么--物质,物质的根本属性是什么--运动。在程序世界里,Data代表了物质,algorithms代表了运动,舍此之外,再无其他(如有,请举例)。
另外,请askbill(天才與瘋子)说中文好吗?虽然俺的英文凑活还能看懂,就是太别扭,谢谢 :-)
TsuLeon 2001-10-03
  • 打赏
  • 举报
回复
学习
KKDogInBJ 2001-10-03
  • 打赏
  • 举报
回复
to cber:
"我认为OO中将功能(动作)看作对象不妥。"
我认为,在OO分析中将动作(或许叫事件更贴切)抽象成对象是很自然(必然?)的事。举个例子来说,打电话是个事件,它被抽象成一个类对象,拥有其方法--拨号,拥有其属性--号码,这不是一个正常而完整的对象吗?更甚,我窃以为若要用100%的OO思想去看待世界,所有的对象都应只包含它自己的属性和于这些属性及其贴近的方法,所有其他的“方法”实际上应该被剥离出来成为独立的事件类。目前,我们构造一个汽车对象,不光包含了它的属性,如型号等,还常常将发动、刹车等方法包含了进去。不可否认,某些时候这给我们带来直观的概念和实作上的便利,但从纯OO的思想上来说,这并不是好的做法。不是吗?发动、刹车等事件不是只有汽车特有的,摩托车同样有,所以,它们应该被当作事件对象独立出来。
GP遵循了这种思想,它将“属性”和“方法”极大的分离。其中的algorithms从本质上来说应当是个事件对象。
所以,我个人以为,GP没有脱离出OO的范畴。不可否认,GP对我们的编程习惯,甚至分析思路带来了极大冲击,但它还是从属于OO的,我们自我感觉分析思想比OO分析有了变化,不是说GP就超脱了OO,那只是因为我们以前还不够OO,而GP更OO。
以上个人观点,^_^。
KKDogInBJ 2001-10-03
  • 打赏
  • 举报
回复
to cber:
"我认为OO中将功能(动作)看作对象不妥。"
我认为,在OO分析中将动作(或许叫事件更贴切)抽象成对象是很自然(必然?)的事。举个例子来说,打电话是个事件,它被抽象成一个类对象,拥有其方法--拨号,拥有其属性--号码,这不是一个正常而完整的对象吗?更甚,我窃以为若要用100%的OO思想去看待世界,所有的对象都应只包含它自己的属性和于这些属性及其贴近的方法,所有其他的“方法”实际上应该被剥离出来成为独立的事件类。目前,我们构造一个汽车对象,不光包含了它的属性,如型号等,还常常将发动、刹车等方法包含了进去。不可否认,某些时候这给我们带来直观的概念和实作上的便利,但从纯OO的思想上来说,这并不是好的做法。不是吗?发动、刹车等事件不是只有汽车特有的,摩托车同样有,所以,它们应该被当作事件对象独立出来。
GP遵循了这种思想,它将“属性”和“方法”极大的分离。其中的algorithms从本质上来说应当是个事件对象。
所以,我个人以为,GP没有脱离出OO的范畴。不可否认,GP对我们的编程习惯,甚至分析思路带来了极大冲击,但它还是从属于OO的,我们自我感觉分析思想比OO分析有了变化,不是说GP就超脱了OO,那只是因为我们以前还不够OO,而GP更OO。
以上个人观点,^_^。
hydland 2001-10-03
  • 打赏
  • 举报
回复
up
Sword_Sharp 2001-10-02
  • 打赏
  • 举报
回复
up
Sword_Sharp 2001-10-02
  • 打赏
  • 举报
回复
gz
gigix 2001-10-01
  • 打赏
  • 举报
回复

to sevecol:恐怕这个问题很难答,至少现在很难答。因为发明GP思想的人,实际上也就是发明OOP的那一拨人。现在使用GP的人多半也是从OOP转过去的。在很短一段时间内,恐怕很难为GP总结出系统的思想和使用原则——myan知道Design Patterns Explained这本书,其中除了讲述面向对象的设计模式之外,还系统讲述了OOP的原则和策略。什么时候在GP方面也有这样一本书,也许我们的问题就有答案了。
gigix 2001-10-01
  • 打赏
  • 举报
回复

to myan:请问老兄能不能先开个课,讲讲在对真实世界的模拟中GP怎样起作用?我现在对这个特别感兴趣,因为我不知道OOP能做的那些事情,用GP应该怎么做。
sevecol 2001-10-01
  • 打赏
  • 举报
回复
to SnowFalcon(恶魔吹着笛子来):
我们在这里比不是讨论OO和GP谁对谁错,而是讨论OO和GP思想是不是一脉相承的.
举个不是很好的例子,在windows下编写程序,我们知道大部分程序用MFC编写起来要方便点,但我们
不是说MFC是对的,不用MFC就错了.
gigix 2001-10-01
  • 打赏
  • 举报
回复

sevecol言之有理。这个帖子,尽管没有讨论出一个是非,却已经相当有价值了。我最喜欢C++版的,就是这种争论问题的风气,让人感到无端快乐。

其实JAVA也涉及很多很多有意思的东西,但JAVA版似乎少见到这样的争论。相比之下还是这里比较有趣。

对了:清华大学有“计算机语言”这个专业的研究生,不是理科是文科,进门考的专业课是“语言学概论”、“现代汉语”。不知道有没有这个专业的高手,提点意见?
sevecol 2001-10-01
  • 打赏
  • 举报
回复
to gigix(透明):
其实这个问题本来就是没有答案的,我们在这里讨论,只是大家交流一下思想,这样能做到取长补短.是自己的视野更加开阔.
cber 2001-09-30
  • 打赏
  • 举报
回复
我现在也有点晕了:(
不管了,回家几天把脑袋理清楚后再来。
I'll be back^_^
sunc 2001-09-30
  • 打赏
  • 举报
回复
造车的英雄未必是名车fan
加载更多回复(104)

70,020

社区成员

发帖
与我相关
我的任务
社区描述
C语言相关问题讨论
社区管理员
  • C语言
  • 花神庙码农
  • 架构师李肯
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧