OOP范式在真正复杂系统中的极限?

时间:2009-08-08 17:25:35

标签: oop

之前我问了一个关于Dataset vs Business Objects的问题 .NET Dataset vs Business Object : Why the debate? Why not combine the two?

我想在这里概括一下这个问题:OOP是否真的适合非常复杂的问题?我们以MMO游戏引擎为例。我根本不是专家,但在阅读本文时,显然OOP远远不够:

http://t-machine.org/index.php/2007/11/11/entity-systems-are-the-future-of-mmog-development-part-2/

总结如下: 使用实体系统编程非常接近使用关系数据库进行编程。将ES称为“面向关系编程”的形式并不是不合理的。

OOP是不是试图摆脱这里要留下的东西?

OOP是非线性的,关系是线性的,两者都是必要的,这取决于系统的部分,所以为什么试图消除Relational只是因为它不是“纯粹的”对象。 OOP本身就是目的吗?

我的问题不是OOP有用。 OOP是有用的,我的问题是为什么纯粹主义者想要做“纯粹的”OOP?

12 个答案:

答案 0 :(得分:8)

作为链接帖子的作者,我想我会提出几点想法。

仅供参考:我在19​​97年开始认真地(即商业工作)使用OOP / ORM / UML,我花了大约5年的日常使用才能真正擅长恕我直言。到那时,我已经用ASM和非OOP语言编程了大约5年。

这个问题可能是不完美的措辞,但我认为这是一个很好的问题,可以自问和调查 - 一旦你理解了如何更好地表达它,你就会学到很多有用的东西。 p>

“那么OOP是不是试图摆脱这里留下的东西?”

首先,请阅读Bjarne的论文:http://www.stroustrup.com/oopsla.pdf

恕我直言,任何人都不应该在没有阅读那篇论文的情况下教授任何OOP(并且在他们“学会”OOP之后重新阅读)。很多人误解了他们正在处理的事情。

<> IME,许多大学课程都不能很好地教授OOP;他们教人们如何编写方法,类以及如何使用对象。他们教的很差为什么你会做这些事情,想法来自哪里等等。我认为很多误用来自于:几乎是一个盲人领导盲人的案例(他们不是'在“如何”使用OOP时,他们只是盲目“使用OOP”。

引用该论文的最后几段:

“你如何支持优秀的编程技术和优秀的设计技术比标签和流行语更重要。基本思想只是通过抽象来改进设计和编程。你想隐藏细节,你想利用系统中的任何共性,你想让这个价格实惠。

我想鼓励你不要让面向对象成为毫无意义的术语。 “面向对象”的概念经常被贬低: - 把它等同于好, - 将其等同于单一语言,或 - 接受一切以面向对象的方式。

我认为除了面向对象的编程和设计之外,还有一些必不可少的技术。但是,为了避免被完全误解,我想强调一点,我不会尝试使用编程语言的严肃项目 - 这至少不支持面向对象编程的经典概念。除了支持面向对象编程的工具之外,我想 - 和C ++提供的功能超出了对直接表达概念和关系的支持。“

现在......我问你......在你见过的所有OOP程序员和OOP项目中,有多少人可以诚实地声称已经遵守了Bjarne的要求?

IME,低于大多数人。

Bjarne表示:

“基本思想只是通过抽象来改进设计和编程”

......但是很多人为自己创造了不同的含义,例如:

“根本的想法是OOP是好的,而且一切都不是OOP是劣等的”

顺序编程ASM的程序员,然后是ASM,然后是pascal,然后是C,然后是C ++,并且已经暴露于编程预封装等的混乱中,往往会更好地理解这些东西。他们知道为什么 OOP出现,它试图解决的问题。

有趣的是,OOP 试图解决每个编程问题。谁曾说过它,说今天怎么谈呢?

它针对的是少数问题,这些问题在您的项目越大越严重时就会非常危险,而且在解决问题时它会介于“好”和“非常好”之间。

但即使是其中一些,也没有比仅仅“好”的解决方案更好;还有其他更好的范例...

当然,所有恕我直言;)

答案 1 :(得分:5)

任何显着复杂性的系统都不是线性的。即使你非常努力地使系统成为一个线性过程,你仍然依赖于磁盘,内存和网络连接这些可能不稳定的东西,所以你需要解决这个问题。

我不知道有人认为OOP是最终答案。这只是一种处理复杂性的方法,试图将各种问题限制在尽可能小的范围内,以便它们在爆炸时所造成的损害最小化。我的问题是它假设完美是可能的。如果是的话,我同意OOP是没有必要的。对我来说,直到有人想出一个更好的方法来减少我犯的错误数量。

答案 2 :(得分:4)

请阅读有关实体系统的文章,该文章将ES与OOP进行比较,对于OOP的几个方面来说,这是明显错误的。例如,当有100个类的实例时,OOP并不强制要求在内存中加载100个类方法,只需要一个。 ES声称能够比OOP“更好”的所有东西因为它有“组件”和“系统”,OOP也支持使用接口和静态类(和/或单例)。

而OOP更自然地适应现实世界,因为任何真实的或想象的问题域,包括多个物理和/或非物理项目和抽象,以及它们之间的关系,可以用适当设计的层次模型建模OOP类结构。

答案 3 :(得分:3)

我们尝试做的是在关系系统之上放置OO样式。在C#land中,这为我们提供了一个强类型系统,以便可以编译和测试从头到尾的所有内容。数据库很难被测试,重构等等.OOP允许我们将应用程序组织成关系不允许的层和层次结构。

答案 4 :(得分:1)

你有一个理论问题。

首先,请允许我同意您的观点,即OOP不是解决所有问题的解决方案。这对某些人来说很好,对其他人来说并不好。但这并不意味着它不会扩大规模。使用OOP设计了一些非常复杂和庞大的系统。

我认为OOP如此受欢迎,因为它值得拥有。它解决了一些相当奇妙的问题,很容易用对象来思考,因为我们可以在不重新编程的情况下做到这一点。

因此,除非我们能够提出一个在实际生活中有效的更好的替代方案,我认为OOP是一个非常好的主意,关系数据库也是如此。

答案 5 :(得分:1)

对于OOP可以处理的内容确实没有限制 - 就像C可以处理的内容或装配器没有实际限制一样。所有这些都是图灵完成的,这就是你真正需要的。

OOP只是为您提供了一种更高级别的方法来分解程序,就像C是比汇编程序更高级别一样。

关于实体系统的文章没有说OO不能这样做 - 实际上,听起来他们正在使用OOP来实现他们的实体,组件等。在任何复杂的域中,都会有不同的方法来分解它,并且使用OOP可以在某个时刻将其分解为对象/类级别。这并不排除使用更高级别的概念框架来设计OOP系统。

答案 6 :(得分:1)

在大多数情况下问题不是面向对象的方法,问题在于底层硬件的性能和实际开发。

OO范式通过为我们提供现实世界的隐喻来实现软件开发,我们是否有概念来定义世界中真实对象的共同接受和预期属性和行为。是人类塑造事物的方式,我们能够解决大部分问题。

理论上,您可以使用OO定义游戏,系统或其他任何方面。在实践中,如果你这样做,你的程序将只是表现得太慢,所以范式被优化搞砸了,这种优化将模型的简单性与性能交换起来。

通过这种方式,关系数据库不是面向对象的,所以我们在代码和数据库之间构建了一个面向对象的层...通过这样做,你失去了数据库的一些性能和一些表现力,因为,从OO范例的观点关系数据库是一个完整的类,是一个提供信息的非常复杂的对象。

从我的观点来看,OO在理论意义上是一种近乎完美的方法,因为它与我们人类思考的方式紧密相关,但它与计算开发的有限资源不相符合......所以我们采取捷径。在和,性能远比理论组织或清晰度重要,所以这个捷径成为标准或通常的做法。

也就是说,我们正在调整理论模型以适应当前的局限性。在70年代后期的cobol时代,面向对象根本不可能......它会暗示很多方面而且性能太低所以我们使用了简化的方法,所以简化了你没有对象或类,你有变量..但在那个时候,这个概念是一样的。变量组描述了相关的概念,今天的属性将成为一个对象。控制序列基于变量值,用于替换类层次结构等。

我认为我们已经使用OOP很长一段时间了,我们会继续使用它很长一段时间。随着硬件功能的提高,我们将能够简化模型,使其变得更具适应性。如果我完美地描述(几乎)猫的概念(涉及许多涉及的概念的描述),那么概念将能够在任何地方重复使用......这里的问题不是,正如我所说,与范式本身,但我们有限制实施它。

编辑:回答有关为何使用纯OO的问题。每个“科学”都想拥有一个完整的模型来代表事物。我们有两个描述自然的物理模型,一个在微观层面,一个用于宏观层面,我们希望只有一个,因为它简化了它为我们提供了更好的方法来证明,测试和开发事物。使用OO,同样的过程适用。如果系统不遵循一套精确的规则,则无法分析测试和证明系统。如果你在一个程序的范例之间进行更改,那么你的程序就无法正确分析,必须在每个程序中进行分析,分析然后再次进行分析以确定相互作用是正确的。理解系统要困难得多,因为事实上你有两个或三个系统以不同的方式进行交互。

答案 7 :(得分:1)

伙计们,关于ORM的问题不是OOP吗? OOP是一种编程风格 - 实际上比较的是映射到对象的关系数据库。

OOP实际上不仅仅是ORM!它不仅仅是继承和多态!它是一种极其广泛的设计模式,最重要的是它是我们对编程本身的思考方式。

Jorge:你可以指出优化部分 - 你没有添加的是这一步应该在最后完成,在99%的情况下,慢速部分不是OOP。

现在简单明了:OOP样式添加了所有主体(干净的代码,使用设计模式,而不是深层继承结构,让我们不要忘记单元测试!)这是让更多人了解你的方法中写道。这反过来又是公司保持商业安全的必要条件。这也是小团队与社区更好理解的接受者。它就像编程语言本身之上的通用元语言

答案 8 :(得分:1)

从纯粹主义者的角度来谈论概念总是更容易。一旦你面对现实生活中的问题,事情变得更加棘手,世界不再只是黑白分明。就像文章的作者非常透彻地指出他们做OOP一样,“OOP纯粹主义者”告诉你OOP是唯一的方式。事实介于两者之间。

没有一个答案,只要你了解不同的方式(OOP,实体系统,函数式编程等等),并且可以充分说明为什么你在任何给定的选择中选择一个情况你更有可能成功。

答案 9 :(得分:1)

关于实体系统。这是一个有趣的概念,但它没有带来任何新的东西。例如,它声明:

  

OOP样式将为每个Component提供零个或多个方法,某些外部事物必须在某个时刻调用。 ES样式是每个组件没有方法,而是连续运行的系统一次一个地运行它自己的内部方法对不同的组件。

但是,与马丁福勒的反模式称为“贫血领域模型”(现在广泛使用,实际上)link不一样吗?

所以ES基本上是“纸上的想法”。为了让人们接受它,它必须通过工作代码示例来证明。文章中没有一个单词关于如何在实践中实现这个想法。没有任何关于可伸缩性问题的评论。没有任何关于容错的说法......

至于你的实际问题,我没有看到文章中描述的Entity Systems如何与关系数据库类似。关系数据库没有文章中描述的“方面”。实际上,基于表数据结构的关系 - 例如,在处理分层数据时非常有限。比例如对象数据库更有限......

答案 10 :(得分:0)

您能澄清一下您在这里要比较和证明的确切内容吗? OOP是一种编程范式,是众多编程范例之一。这不完美。这不是一颗银弹。

“面向关系的编程”是什么意思?以数据为中心?好吧,微软正在转向更加以数据为中心的编程风格,直到他们放弃Linq2Sql并完全专注于他们的O / RM EntityFramework。

关系数据库也不是一切。有许多不同类型的数据库体系结构:分层数据库,网络数据库,对象数据库等。而那些可能比关系更有效。关系是如此受欢迎,原因几乎与OOP如此受欢迎的原因相同:它很简单,很容易理解,而且通常效率很高。

答案 11 :(得分:0)

具有讽刺意味的是,当oo编程到达时,构建更大的系统变得更加容易,这反映在软件推向市场的过程中。

关于规模和复杂性,通过良好的设计,您可以构建相当复杂的系统。 请参阅ddd Eric Evans,了解处理复杂性的一些原则模式。

然而,并非所有问题域最适合所有语言,如果您可以自由选择语言,请选择适合您的问题域的语言。或者如果更合适,建立一个dsl。

我们毕竟是软件工程师,除非有人告诉你如何完成工作,只需使用最好的工具,或者写下来:)