00:00
讲完封装以后呢,我们接着来给大家看一下面向对象编程里边的继承,啊来来聊聊这个继承这个话题,呃,那么还是老规矩,就是说我们在讲继承之前呢,我们先来说一下为什么需要继承,那也就是说我们去学一个新的东西,总是有一个原因的,对不对?就说这个go的设计者,他在设计这个继承的时候,为什么需要有继承?那么这个继承能够给我们编程带来什么好处?我们首先要把这个弄清楚,OK,那么我们来看看为什么需要继承,我这里呢有一个小问题。呃,假如我们要去看一,我们要去写一个学生考试系统,比如比如说下面这个叫学生会管理系统,那这里面呢,有各种各样的学生。有各种各样的学生,那比如说现在呢,呃,我们有这么一个需求,我们需要记录各种学生考试的成绩。那你想一想,这个时候你会怎么做?啊,OK,先把这个问题提到这里,大家呢先思考一下,我呢先板书一下,好吧,先板书。
01:06
这是面向对象的继承。我把它呢也先写到这里。三大特性的封装。对吧,这个就是继承了。抽象继承。三的特性。这个地方写的是封庄。把它稍微的改一下啊封装。好,现在呢,我们说一下它面向对象特性的继承。往下拉一拉。这个还挺长哈,还挺长,OK,面向对象编程特性。三大特性。之继承。好,我们把它本书一版,嗯,那既然是继承呢,我们还是老规矩,先看一个问题,这里呢就引出。引出继承的必要性。对吧,要引出继承必要性,大家听的时候呢,才会掌握到他的一个精髓。
02:03
掌握到它的精髓。好,我们来一个标题三。那个标题层我们来看看他有哪些必要呢?就说为什么需要继承对吧,为什么需要继OK,那这个问题我已经抛出来了。一个问题就是我们要记一个学生的考试系统,那么这个地方呢,我们怎么来处理的问题?来,我们先走一下代码。我们来走一下代码,大家看一下。纸。走下代码。OK,给大家板书一下。那现在呢,我们来写一下这个代码,好吧,我们来写一下代码,现在呢,我们因为是继承嘛,所以说我新建一个文件夹。继承叫对吧,然后呢,DEMO。我新建一个文件。这个文件我们仍然叫面点高。对吧,然后呢,把前面共用的部分我们拿来用一下。
03:01
把这个包包先去掉。把这个保险去掉。好,去掉它,我们把它删掉就行啊,去掉它就行了。那么这个地方呢,我们要写一个学生考试系统。编写一个学生考试系统。那既然是学生考试系统的话,大家想一想怎么来做呢?嗯,那我这样子来处理好不好?假设我们有小学生要考试。小学生。那小学生我肯定就会建一个结构体对吧,叫pup PU piil,然后呢,它是一个结构druct里面呢,有这么几个类型,呃,有这么几个字段,一个是他的名字,一个是他的年龄,还有呢,就是他的考分。他考试成绩是多少,比如说也是个特吧,完事,那既然是小学生要考试,那么小学生呢,我们认为它有这么几个函数,第一个呢,就是。
04:04
显示他的成绩,就是它显示他的成绩。显示他的成绩好,那我就给他绑,绑定一个方法,这个没问题吧,放。比如说这有个学生。P puil,这是学生,然后呢,叫受。显示他的成绩吗?Show for。Show for。好,这里面呢,就直接输出他的成绩就行了,Print。好,我说我我来格式化一下,格式化一下就是学生名。小这样写啊,小学生也叫学生名吧,学生的名字。学生名字对吧,给他输出来,然后呢,他的年龄给他输出来。年龄也输出来,他的成绩也给他输出来。那我怎么输出呢,输完了过后,咱们是不是应该来一个换行啊。
05:03
他的这些成绩我都可以直接访问到这里,我就不去写那个get set的方法了,好吧,因为我就在一个文件里面写,我也不去封装它了。现在因为我是讲继承嘛,所以说我就直接让他公开访问就行了,名字要年龄age,然后呢,还有成绩写完了。这就是他显示的成绩,那么第二个呢,我们当然它有一个什么呢?有一个考试啊,这个我改一下啊,就是给他设置分数。就是他考完了过后呢,有一个score。就是给他设置乘积,那设置乘积,我就把这个乘积给它写进去,Score,比如个flow,呃,Int啊考分整数怎么给他设置呢?那你当然这边你可以做些业务判断。这可以做一些业务,出业务判断,我这里就不去判断了,好吧,我就直接给他一个值,就是B点什么呢?靠,等于你传进来的这个成绩完事,但你标准的写法应该有些判断,比如说他这个成绩是不是在一定范围里边是吧,我们考试成绩呢,比如说在一到100之间,你不能说它有个成绩是负二啊,这个就不合理了,但这里呢,因为我是讲继承,所以说这个业务判断我就忽略了,明白好,那么我们这还有一个呢,就是显示他正在考试的状态。
06:28
比如说这个地方显示他正在考试。好的,这边我说出一句话。说说一句什么样的话呢?我说小学生正在考试,OK。小学生。学生正在考试。考试中。明白,好,这就写完了,大家看到这个小学生成绩呢,小学生的一个很简单的一个测试就出来,有显示成绩,有设置成绩,有考试状态的测试,好我们来试用一下先。测试一下。
07:02
这个就比较简单,首先我去创建一个小学生pupil。对吧,这个很简单,Pup的话呢,我给他一个地址啊,这个我也不去用,不去用这个构造函数了,好吧,直接给他就行了,名字。这个人的名字呢?比如叫汤姆。呃,然后他有他的年龄,我们也给他一下年龄,比如说这个人18岁,呃,小学生嘛,十岁,OK,他的其他情况我们就来调用他了,比如说小学生,他先进行一个测试。Testing,他考试,考试完了过后对不对,我们给他测试成绩,设设一个成绩sat。SC。那比如说他考完了过后呢,他考了九十九十分对不对,然后我们把他的信息输出。p.show info。Info好写完了,那么我们现在跑一跑这段代码有没有问题,诶看这好像有毛毛病是吧。
08:02
呃。说诶这怎么写错了啊type。Type。其他没毛病吧,哎,这还有个问题,这少了一个什么呀,少了一个逗号,来,我们先把它跑起来,跑起来,CD点点CD点点CD到我们这一个X。然后呢,我们go wrong,诶这个代码好像还有问题,看哪里有错。这里。And fan?Testing,哦,这我们少写了个T。是不是少写了个T啊,把它加进去就可以了。妹,点够跑起来,我们看一下这输出的信息,小学生正在考试中,然后最后成绩是小学生的名字为汤姆。年龄为十岁,成绩为90分,没问题吧?问题在哪里呢?问题在这儿,你有小学生考试,那当然我们还有大学生要考试,对不对?有这种可能性吧,比如说我们还有大学生。
09:01
除外。除此之外,我还有研究生。研究生,那这个时候你怎么处理?请问你这个时候怎么处理?那必然,因为我们小学生考试,你这就不你你大学生考试,这至少不能提示小学生正在考试吧,因为你考试的内容不一样吗?是不是这样子的,你小学生考的是呃,小学数学,那大学生考的是高数。对吧,尽管信息和这个设置成绩咱们是可以一样,但是他这个地方testing它考的内容不一样,是这意思吧,那你这个时候你要做这个开发,你只能这么干了。听我说你可能只能这么干,粘贴一份下来,注意看啊,麻烦已经来了。因为你是大学生。哦,我们叫大学生,那我们就写个graduate。Graduate啊graduate那他的名字年龄曾经没有变化,就是这个结构体的名字变了,这个地方也要变了啊,因为你是给他绑定一个方法吗。
10:02
对吧,你肯定要改啊,那就是说学生名字年龄成绩一样的,当然这个地方你干脆我就不改了,我就也叫P没问题吧。同时你给他设置成绩也要绑定到graduate这个结构体类型的指针类型是这意思吧,然后这张也不用变化,紧接着呢,你要显示成绩,你要绑定到graduate这个结构体上面去,这唯一改了一下大学生。那同学们想一想啊,这个时候我们是不是也是可以来测试的呀?是不是我们是不是也可以测试一下,我们刚才写的对大学生考试有没有正确。这是二。那我粘贴拷贝那graduate。Graduate,然后这边呢,我们给他来一个graduate,好,这个地方大学生我们几个叫叫Mary,他多少岁了呢,他20岁了,当然你在调用的时候肯定是这样调。
11:00
对不对,那调完了之后,我们输出一下。我们可以看到这篇信息,大家看这里,他说大学生正在考试,学生成绩为Mary,年龄20,成绩也是90分,因为我这设的呢,仍然是90,没有改,对吧。好,同学们,看到这地方代码是不是已已经出现了一些小问题啊?说老师没有没有出现问题啊,大家有没有发现我们代码已经出现了冗余。哪里出现了冗余?同学们请思考你这个pupil。它的字段三个和我们GRADUATE3个字段是不是一模一样,这是第一点已经冗余了,第二点我们发现你这个pupil它的这个函数和这个函数是不是跟我们graduate这个函数和这个函数是完全一样的。是不是完全一样,但是呢,唯一不一样的就是这个testing,小学生这个结构体啊,Pup这个结构体,它的内容是输出小学生正在考试中,而大学生。
12:00
大学生,他说的是大学生正在考试中,我们发现其实他们唯一不一样的就是这个函数而已。看到没有,就这一个函数不一样,但是为了这一个函数不一样,我们却写了两份几乎相同的代码。几乎相同。那问题来了,代码冗余。是不是代码已经出现冗余了?而且你想一想,你除了有大学生,你是不是还有其他学生呢?比如说高中生。高中生。对不对?还有其他的学生,那难道你每个都来一份吗?显然,这个问题已经摆在我们面前了。这已经摆在我们面前,所以说问题咱们已经发现了什么呢?通过走代码,我们发现的问题是代码冗余,好,先把这个代码先拿过来,同学们。我把这个代码直接放到拷贝一下啊,直接放到我们这边好不好,这些老师就不一个个不一个个的截图了,因为截图太累啊,这段代码我就放好了,大家能看懂吧。
13:05
应应该能看懂,是不是也比较简单,那么对于这个代码,我们发现他的问题是什么呢?我们对上面这个代码做一个小结。对,上面。啊。对上面代码的一个小结。小结是什么呢?就是我们发现他有些问题对不对?我们发现他有些问题,好,我给大家一个板书。我们发现的问题呢,有这么几个,第一个。第一个。就是。就是这样写啊,就是pupil。Pupil和graduate。Do it。看这是怎么写的啊。我跟他保持一致。Graduate。
14:01
和graduate这个结构体,它们两个结构体啊,两个结构体的字段和方法几乎一样。是不是几乎一样,但是我们却我们,但是我们。但是我们却写了。却。写了两份几乎相同的代码,写了相同的代码。对吧,这是是不是一个问题啊,同学们是不是相同代码,那这样子的话就出现了什么呢?出现了出现代码冗余。而且大家看到,而且它并不利于代码的维护,而且代码代码并不利于维护。代码不利于。利于维护。同时呢,也不利于扩展,同时也不利于也不利于什么呀,功能的扩展。
15:03
是不是意思,你想一想,同学们打开我们源代码,假设,假设我们这个要加一个方法,比如说呃,我们认为graduate就是大学生和小学生呢,他们都有一个方法叫可以,他们会什么呢?他们会做算术题。假设啊,假设我要给pupil和graduate都加一个相同的方法,是不是你要加两分?是不是你想一想,如果我给一个小学生加一个,呃,他可以,他可以去做算术题的方法,那么我要给这个graduate也要保证另一个方法,所以说你会发现你仍然不利于代码,不利不利于代码的维护,同时呢,也不利于功能的扩展。他也不利于功能,功能的扩展,这两个都有问题。那既然如此,同学们既然如此,那下面呢,老师就要给大家讲一个东西了。啊,什么东西呢,既然你这有这个问题,那我们这个勾勒的设计者,他就提出了一个概念,叫什么概念呢,就引出。
16:07
解决方法。解决方法就是继承。通过。通过继承的方式。继承的这个方式啊方式来解决。好,终于啊,现在呢,我们写了一段代码过后,我们引出了继承这个概念,就说为什么需要继承呢?因为我先抛了一个问题,告诉你们,没有继承,我们就有可能出现代码冗余,在面向对象编程的时候,肯定会出现代码冗余。对不对,肯定不利于我们代码的维护,因此继承这个知识点就呼之欲出啊,就就就让我们把它。把它这个互换出来了,我们就要给他讲继承到底是怎么去做好,同学们,那关于这个为什么需要继承,或者说继承这个问题的引出呢,我们就先说到这里,那下面我们就来说继承到底怎么实现,大家先把这个案例先体会一下啊,先体会一下。
17:02
哦,大家看看这个问题就是代码复用性的问题。好继承,呃,就是它可以代码复用性很高,你看刚才我们说的说的实际上也是一个问题,对不对,你看这个两份代码完全相同,何必写两份相同代码呢。对不对,所以说我们要提出的问题呢,也是这样子的。提出问题。对吧,相同代码这样子呢,代码就重复了嘛,复用性不强啊,代码服务用性不一样。代码复用性。啊,不行。复用性。啊,那不强的话就出现冗余了嘛,啊OK,好,关于这块我们先说到这。
我来说两句