0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示

关于单片机编程的OO思想学习方法和经验分享

UtFs_Zlgmcu7890 来源:互联网 作者:佚名 2017-12-16 07:23 次阅读

1.人脑的限制

由于受到电脑信息处理功能的影响,因此于20世纪60年代初产生了以信息处理论为基础的认知心理学。美国心理学家乔治·米勒在信息记忆上的研究成就,为新兴的认知心理学提供了理论的证据。

虽然当时的心理学家已将信息处理的历程,大致区分为感官记忆(2秒以下)、短时记忆(15秒以下)与长时记忆,但短时记忆的性质及其重要性,则是在乔治·米勒1956 年发表研究报告《神奇的数字7 +/- 2,我们信息加工能力的局限》之后才被确定的,即米勒魔术——人类只能记住和处理7加或减2项内容。

后来的证据表明基数可能少到3或4,这个数字代表大脑“暂存器”解决问题时所能保存的信息容量。无论实际数目是多少,如果要求普通人同时考虑大约15件事情,实际上最多只能记住和处理其中9件甚至更少。

如果要求处理的事情更多,一次只有几件可以同时处理,其它的会被快速切入或切出暂存器。想一想去商店采购15件东西,如果没有一份购物清单,你很可能漏掉东西或买回来的东西数量不正确。同样的道理,如果需求列表或产品清单中的事项成千上万,那么你的大脑根本没办法处理这样复杂的事情,除非将它分解成更小的结构化分组。

2.核心域和非核心域

一个软件系统封装了若干领域的知识,其中一个领域知识代表了系统的核心竞争力,这个领域被称为“核心域”,其它领域称为“非核心域”。虽然更通俗的说法是“业务”和“技术”,但使用“核心域”和“非核心域”更严谨。

非核心域就是别人的领域,比如,底层驱动、操作系统和组件,即便你有一些优势,那也是暂时的,竞争对手也能通过其它渠道获得。非核心域的改进是必要的,但不充分,还是要在核心域上深入挖掘,让竞争对手无法轻易从第三方获得。因为在核心域上深入挖掘,达到基于核心域的复用,这是获得和保持竞争力的根本手段。

要达到基于核心域的复用,有必要将核心域和非核心域分开考虑。因为人脑的容量是有限的,而过早地将各个领域的知识混杂,会增加不必要的负担,从而导致开发人员腾不出脑力思考核心域中更深刻的问题。

正因为人脑的容量和运算能力有限,待解决的问题的规模一旦变大,就必须分而治之,因为核心域与非核心域的知识都是独立的。比如,一个计算器要做到没有漏洞,其中的问题也很复杂。如果不使用状态图对领域逻辑显式地建模,再根据模型映射到实现。而是直接下手编程,领域逻辑的知识靠临时去想,最终得到的代码肯定破绽百出。其实有利润的系统,其内部都是很复杂的,千万不要幼稚地认为“我的系统不复杂”。

3.职责转移

在面向过程编程时,由于主程序承担的责任太多,要确保一切正确工作,还要协调各个函数并控制它们的先后顺序,因此经常会产生非常复杂的代码。很多时候变化是不可避免的,而功能分解法却又无法应对可能出现的变化。一旦修改代码,则bug越来越多。更重要的是,由于人类的大脑无法做太多复杂的处理,记忆力和理解力也是有限的。因此面对复杂的软件开发时,主程序不能做太多的事情,必须通过“分离关注点”进行职转移责。

假设要乘出租车去机场,一种方式是告诉司机,按照“启动、右转、左转、停止”等单独的接口去机场。这种方式需要乘客对自己的行为负责,乘客知道每个城市去机场的路线。

既然用户的需求总是在变化之中,我们将无法阻止变化。与其抱怨变化,不如改变开发过程,从而更有效地应对变化,面向对象编程就是这样作为对抗软件复杂性的手段出现的。

在面向对象编程时,另一种方式是告诉司机,“请载我去机场”。尽管具体实现在广州、北京或上海等不同城市中是不同的,但在任何城市都可以这么说。因为司机知道怎么去机场,司机对自己的行为负责,并信任司机知道如何执行,这就是职责转移,显然这种方法比功能分解法要容易得多。

由于每个对象都对自己的行为负责,因此必须有方法告诉对象要做什么。而方法都被标识为能够被其它对象调用,这些方法的集合被称为对象的公开接口。其形象的比喻为,“将软件对象看成具有某种职责的人,他要与其他人协作完成工作。”

>>>1.1.2 OO机制

面向对象的编程是由类(class)这种结构实现的,C++类的概念是对C结构概念扩展。因此表面上看起来这些特征与面向对象编程语言有很大的关联,但实际上能用任何一种语言实现。不管实现语言如何,任何大的软件系统都会以某种形式使用抽象、继承或多态性。

1.封装

封装是OO方法中的一个重要原则,其含义是将封装视为任何形式的隐藏,对外形成一个边界,只暴露有限的对外接口使之与外部发生联系。封装不仅仅是将对象的全部属性和全部操作结合在一起,形成一个不可分割的独立单位(对象),而是发现变化将其封装。

抽象是实现封装的分析工具,抽象可以使我们专注于应用程序最本质的方面,同时忽略细节。在确定如何实现功能之前,先关注对象是什么?做了什么?更具体地,抽象是总结一类对象的共同特征创建类的过程,包括数据抽象和行为抽象

数据抽象是数据和处理方法的结合,即封装数据和函数到类中的能力,因此又将数据抽象称为信息隐藏或封装,信息隐藏是一种软件设计思想。由于不必知道内部结构,因此可以将数据当作黑盒子来操作。即使将来数据结构发生变化,对外部也没有影响。从而避免程序的各个组成部分过于相互依赖,否则很小的变化也会引起巨大的连锁反应。

在结构化的设计中,通常将代码封装到函数和模块中。因此封装不是OO语言所特有的,但它能将数据结构和行为组织在一个实体中,其主要目的是为使用代码的程序员提供一致的接口,这是面向对象编程的突出特点。尽管如此,面向对象和结构化的代码并不是互斥的,实际上不用结构化代码将无法创建对象。因此在构建面向对象的系统时,在设计中依然离不开结构化的技术。

2.继承

虽然结构化程序设计通过编写一个功能块实现重用,但面向对象程序设计实现代码重用的方法是允许定义类之间的关系。而继承是实现该功能的主要手段,其将不同代码中相同的部分提取出来。即抽取不同类的共同属性和行为创建全新的类,实现代码最大限度地重用。

利用类和继承这两个特性,高效地将抽象数据通过类封装起来,即通过类将同一类对象管理起来。因此可以说类是将数据黑盒子化的工具,而继承可以从其它类继承属性,只需要扩展实现或对实现稍作改进,即可支持软件重用。

在经典的Shape(形状)示例中,Circle(圆形)、Square(矩形)和Star(星形)都直接继承自Shape,这种关系通常被称为is-a关系。因为圆是一种形状,矩形也是一种形状,星形也是一种形状,即Circle、Square和Star都是Shape的扩展。当子类继承自父类时,任何父类能做的事情子类都可以做。

3.多态性

当你要求某人画一个形状Shape时,实际上没有人能完成这个任务。因为形状是一个抽象的概念,所以Shape无法提供绘制代码,必须指定一个具体的形状。有了具体形状,就可以为各种具体形状实现各自的绘图代码。

显然,无论画什么形状,其共性是Draw画图方法,每种形状都可以通过函数指针调用各自的绘图代码绘制自己,这就是多态的意义,即多态允许用相同的方法(代码)在运行中,根据对象的类型调用不同的处理函数。

4.组合

组合是指在类中包含一个对象,且该对象是其它类的实例,开发者将责任委托给所包含的对象完成。组合有两种方式:聚合和组合,这些方式表示了对象之间的协作关系。

聚合就是“可聚可散”的意思,被包含的对象如同一个集合。聚合关系是整体与部分的关系,且部分可以离开整体而单独存在。虽然汽车和发动机是整体和部分的关系,但发动机离开汽车仍然可以存在,所以汽车和发动机是聚合关系。

虽然组合关系也是某种形式的整体和部分的聚合,但部分不能离开整体而单独存在,部分对象与整体对象之间具有同生共死的关系。在组合关系中,部分是整体的一部分,且整体可以控制部分的生命周期,即部分的存在依赖于整体。

虽然花瓣不是一种花,但它是花的一部分,因此它们之间存在一种真正的has-a组合关系,不存在父子关系。同样,头部是由眼睛、嘴巴、鼻子和耳朵组合而成的,如果头部不存在,那么这些部件都不能单独存在。

>>>1.1.3 OO收益

耦合性与内聚性是相辅相成的关系,内聚性描述的是一个模块内部组成部分之间相互联系的紧密程度,而耦合性描述的是一个模块与其它模块之间联系的紧密程度。由此可见,无论使用哪种方法,软件开发的目标是创建符合“高内聚、低耦合”这样的模块。也就是说,每个模块尽可能独立完成某个特定的功能。

如果模块之间做到了低耦合,那么修改一个模块就不需要修改另一个模块。使用模块化最重要的一点是,能够独立修改单个模块,而不需要修改系统的其它模块。一个典型的错误是,使用紧耦合的方式做模块之间的集成,从而使得一个模块的修改会导致其消费者的修改。一个低耦合的模块应该尽可能少地知道与之协作的那些模块的信息,即应该限制两个模块之间不同调用形式的数量,因为除了潜在的性能问题之外,过度的通信可能会导致紧耦合。

内聚性用于评估一个组件(包、模块或配件)中成员的功能相关性,内聚程度高表明各个成员共同完成了一个功能特性或一组功能特性,内聚程度低表明各个成员提供的功能互不相干。如果一个类的方法和属性共同完成了一个功能或一系列紧密相关的功能,这个类就是内聚的。假设有一个这样的类,实现了3种完全不同的功能。如果这3个功能的需求细节发生了变化,这个类也必须跟着改变,从而导致更多的开发和维护成本。因此高内聚就是将相关的行为聚集在一起,而将不相关的行为放在别处。这样做的好处是,如果要修改某个行为,则只在一个地方修改,即可尽快发布。

声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉

原文标题:周立功:OO思想——面向对象编程

文章出处:【微信号:Zlgmcu7890,微信公众号:周立功单片机】欢迎添加关注!文章转载请注明出处。

收藏 人收藏

    评论

    相关推荐

    0基础,我想学好LV,它跟其它编程语言学习方法有什么注意

    就是想高手们分享一下经验,请问高手们我的学习方法对不对?提高自己的学习效率而已,我是真真的零基础啊~~~谢谢!
    发表于 02-27 21:28

    求128单片机学习方法

    求128单片机学习方法
    发表于 01-06 22:38

    单片机学习方法

    学习方法,效果特别好 2>:合理安排时间持之以恒 学习单片机不能 “ 三天打鱼、两天晒网 ”,要有持之以恒的毅力与决 4 心。学习完几条指令后,就应及时做实验,融汇贯通,而不要等几天
    发表于 10-10 13:39

    初学STM32是否有推荐的学习方法、教程和开发板

    大家好,本人只学过AVR单片机,对C语言没有学过,想学习一下STM32,是否有推荐的学习方法、教程和开发板!非常感谢
    发表于 09-14 09:40

    单片机学习方法资料分享

    ,虽然每个系列的功能不一样,但是最基本的编程思想还是一样的,不同的可能就是编译器,程序下载的软件等差别,所以有了51单片机的开发基础之后,学习其他
    发表于 03-11 10:59

    单片机编程思想

    而呆板。这个骨架需要包上皮肉,加上灵魂,这样有血有肉有思想的程序才是我想要的,可是我怎么才能做到呢?朋友,如果您有这方面的经验请指点迷津!或者给我推荐一些关于单片机
    发表于 07-01 04:35

    单片机学习方法和步骤

    学习单片机的动机不外乎有四种:一是为兴趣爱好而学,二是为专业而学;三是为饭碗而学;四是在工作中被逼而学。不管是哪种动机,因主修专业的不同以及电子基础的深浅不同,对于不同的人可能采用不同的学习方法
    发表于 07-15 09:11

    请问STM32单片机学习方法有哪些?

    请问STM32单片机学习方法有哪些?
    发表于 10-26 06:59

    萌新求助,求大佬分享单片机学习方法

    萌新求助,求大佬分享单片机学习方法
    发表于 11-08 08:36

    单片机学习方法和步骤相关资料推荐

    ,根据笔者的亲身学习经验和教授徒弟学习的感受,提出笔者的学习方法和步骤。目录第一步:基础理论知识学习第二步:
    发表于 11-22 08:31

    单片机学习方法和步骤

    学习单片机学习其他学科需要付出更多的努力和代价,不仅要学习理论知识还要练习实际操作,而且主要是在实际操作中才能真正学到单片机技术。因主修专
    发表于 11-30 06:38

    AVR单片机学习方法详解

    详细介绍AVR单片机学习方法,很适合初学者!
    发表于 05-16 17:15 3次下载

    单片机学习方法总结资料分享

    单片机学习方法总结资料分享
    发表于 11-13 20:36 5次下载
    <b class='flag-5'>单片机</b><b class='flag-5'>学习方法</b>总结资料分享

    单片机学习笔记————单片机学习方法和步骤

    ,根据笔者的亲身学习经验和教授徒弟学习的感受,提出笔者的学习方法和步骤。目录第一步:基础理论知识学习第二步:
    发表于 11-14 14:06 5次下载
    <b class='flag-5'>单片机</b><b class='flag-5'>学习</b>笔记————<b class='flag-5'>单片机</b><b class='flag-5'>学习方法</b>和步骤

    梳理单片机学习方法、产品开发流程

    梳理单片机学习方法、产品开发流程
    的头像 发表于 09-21 17:20 367次阅读
    梳理<b class='flag-5'>单片机</b><b class='flag-5'>学习方法</b>、产品开发流程