为什么无法面向对象

条条道路通罗马,能解决问题的都是好办法。

1. 产品需要满足用户需求。
每天都在用windows、ie、word、firefox等,都很好用,但对用户来讲谁关心后面的代码、架构是什么样子。
生产线上的人每天都在用你写的产品,他们只关心产品是否能准确地完成功能,没有故障,操作是否方便。

有很多人觉得架构不好,代码ugly,所以重写产品,下面几个老链接大家可以看看。
Things You Should Never Do, Part I: http://www.joelonsoftware.com/articles/fog0000000069.html
里面提到NetScape的重写等,甚至微软的word也曾打算过重写,好像是这些文章还是别的什么地方提到过一个ftp代码重写了3、4年才完成。

我们每天面对着一行行代码时,是否能多想想这些代码怎样方便的帮助用户完成想要的工作?它们怎样才能帮助公司实现更多的利润,帮助客户实现更大的价值?新的设计思想的运用、代码中隐藏的每个错误会给项目带来什么影响,会给客户造成什么损失?
这些不仅仅是老板、架构师、项目经理的责任,项目中的每个人应该有比较深刻的认识,才能做出好产品。程序员的职业生涯想要往高处走,哪怕是升为一个高级程序员、架构师,都需要不断的将目光关注在这些方面。所以不要一天到晚只盯着代码看问题,总跟代码过不去。

2. 产品需要满足市场需求,满足市场运作策略。
很多程序员出身的,后来做项目经理了,做销售了,不少已经在做老板了,多了解一下他们面临的问题,他们的想法。也许不久之后你也打算创业做老板了。
没有多少项目能够像暴雪那样,动不动写个6、7年,产品推出来还能保证巨大的市场成功,Vista写了5年已经很长,再写个几年可能要失控。尤其国内这种激烈的竞争环境,慢个半拍人家就已经把它做的很好了。
所以老板有市场压力,项目经理需要承担项目周期与质量压力,需要处理各种技术、未知故障风险。

很多时候老板的要求并不是错的,客户的要求并不是不合理的,只是你没有理解,所以都被你宣判为无理的、搞笑的、不适合产品开发的要求。所以心里开始抵触, 不能全面的配合老板、经理实现目标,有时候做出来的东西牛头不对马嘴。最后老板说程序员不可思议,程序员说老板真差,double-lose!

3. 不要盲从。
"不要迷失在技术的海洋中"应当也是这个意思。
看《领域驱动设计》,作者开始就说了这种方法不是万能药,他的不少项目使用这种方法都失败了。看《企业应用架构模式》,作者并不会告诉你你的项目应该用领 域模型、事物脚本还是表模块,要根据实际状况选择。最近刚开始看《分析模式》,每一种模式都从简单到复杂讲述,但一开始作者就提出了根据需求具体选择采用 简单方式还是复杂模型,正确实现需求的就是好模型,不要盲目的为产品做过多假设。
尽管Martin Fowler和Eric Evans都受敏捷思想的影响,这不是关键,其它书籍也差不多如此。他们提供的只是一种方法、思想,具体环境具体运用,开篇不起眼的一些话,在理解了这些思想之后,这些话才是最重要的。
一个经理如果总能按园子里大家的想法来管理、开发产品,极有可能是一个彻底失败的经理。

4. 产品需要积累。
产品的成熟并不是指代码多漂亮,架构多完美,这些东西只占据比较小的分量。产品成熟更多的是指产品功能、性能、稳定性、用户使用性,以及从业务功能、运营部署要求面看起来一定的灵活、扩展性。

很多时候会听到这种话:这个项目这么简单,真搞不懂他们怎么花了那么长时间;这么简单一件事,想不透为什么写的这么复杂。
仔细看过上面推荐的两个链接,结合自己的经验很容易理解,很多非常ugly的代码中隐藏了不少疑难杂症的修复知识,这是一个方面。
另外一个方面,将需求一步步收集起来,将产品从无到有做起来,能够满足用户要求在生产线上运行起来,不是件容易的事情,这个里面很多困难你想不到,交给你重做一次未必比前人做的好。

很多人在学习设计模式,很多人每天都在不断的重构代码,有没有人实际的去关注过,你做的这些工作,真的给产品、给用户带来了多少好处,实现了多少价值。其实脱离实际需求,程序员拍脑袋想的很多东西,花了很大精力去实现,可能从头到尾就没有发挥过作用,或者作用非常有限。
很多时候你发现自己负责的产品很灵活、功能很强,可是到用户那边,到下一个项目/客户,新的需求非常多,不少时候已有架构无法满足。

比较长一段时间内,要象大家讨论的方式来做项目,象不少程序员心中想象的情景去开发一个产品,是不大可能的。我们只能不断的在项目中做小的修改来积累产品,在适当的时候做一些大的调整来改善产品。
如果从产品最开始就采用大家推崇的各种方法、思想来做一个产品,这个产品成功的概率多大?
不要说小公司才有这种烂做法,没有心胸的经理才会否定这种做法,看看Oracle、MS、HP等,看看印度的软件工厂,难道都是采用大家理想的做法?

保证第一个版本可用,第二个版本好用,第三第四个版本能够通用,不是代码层面,而是功能层面的,相信不少公司产品都是这样的战略。这里不仅有市场策略,也有产品项目迭代开发方式,功能的逐步完善、用户反馈等等其它各方面的考量因素。

最后:
看待问题不要太单纯,面向对象也好非面向对象也好,存储过程也好SQL也好,多探讨交流让大家都加深认识就行了,至于实际环境应该采用什么方式,都不能做定论。
不少程序员、开发团队确实是得过且过,对未掌握的东西不大愿意去了解,因陈守旧,也确实是一个方面,有的是本身上进心不够,有的是生活或其它压力太大,工 作的事情只是敷衍。既然是在园子里活跃的,应该大部分不属此列,所以更应该注重的是注意改变自己的视角去分析问题,使自己的技术研究更有针对性方向性,看 待问题更全面。
C语言不是面向对象语言,主要有以下原因: ### 缺乏直接的类和对象支持 面向对象编程的核心概念之一是类和对象,类是对象的抽象模板,对象是类的实例。C语言本身的语法中有直接提供“类”这样的概念,无法像Java、C++等面向对象语言那样方便地定义类和创建对象。例如在Java中可以这样定义一个类: ```java class Person { private String name; private int age; public Person(String name, int age) { this.name = name; this.age = age; } public void sayHello() { System.out.println("Hello, my name is " + name + ", I'm " + age + " years old."); } } ``` 然后可以轻松创建对象并调用方法: ```java Person person = new Person("John", 20); person.sayHello(); ``` 而C语言有这种直接的类定义方式,虽然可以通过结构体模拟类的部分功能,但功能和使用便捷性上远不如面向对象语言 [^2][^4][^5]。 ### 不支持封装特性 封装是面向对象编程的重要特性之一,它将数据和操作数据的方法捆绑在一起,并对外部隐藏对象的内部实现细节,只提供公开的接口。C语言有访问控制机制,结构体中的成员可以被任意访问和修改,无法实现像面向对象语言中私有、保护和公有成员的访问控制。例如在C++中可以这样实现封装: ```cpp class Rectangle { private: int width; int height; public: Rectangle(int w, int h) : width(w), height(h) {} int getArea() { return width * height; } }; ``` 在这个例子中,`width` 和 `height` 是私有成员,外部无法直接访问,只能通过公共方法 `getArea` 来获取矩形的面积。而在C语言中,结构体成员默认是公开的,无法实现这种隐藏数据的封装特性 [^4][^5]。 ### 不支持继承特性 继承允许一个类继承另一个类的属性和方法,从而实现代码的复用和扩展。C语言有提供继承的语法机制,不能像面向对象语言那样定义子类继承父类的特性。例如在Java中可以这样实现继承: ```java class Animal { public void eat() { System.out.println("Animal is eating."); } } class Dog extends Animal { public void bark() { System.out.println("Dog is barking."); } } ``` 在这个例子中,`Dog` 类继承了 `Animal` 类的 `eat` 方法,同时还可以有自己的 `bark` 方法。C语言无法直接实现这种继承关系,虽然可以通过一些技巧模拟,但实现起来比较复杂且不够直观 [^5]。 ### 不支持多态特性 多态是指同一个方法可以根据对象的不同类型而表现出不同的行为。在面向对象语言中,多态通常通过继承和方法重写(覆盖)来实现。C语言有提供多态的直接支持,无法实现方法的动态绑定。例如在C++中可以这样实现多态: ```cpp #include <iostream> class Shape { public: virtual void draw() { std::cout << "Drawing a shape." << std::endl; } }; class Circle : public Shape { public: void draw() override { std::cout << "Drawing a circle." << std::endl; } }; void drawShape(Shape& shape) { shape.draw(); } int main() { Circle circle; drawShape(circle); return 0; } ``` 在这个例子中,`drawShape` 函数接受一个 `Shape` 类型的引用,根据传入的实际对象类型(`Circle`)调用相应的 `draw` 方法,实现了多态。C语言由于缺乏继承和虚函数等机制,无法实现这种多态特性 [^5]。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值