00:02
同学们,我们来完成最后一个改进,就是说我们要用结构体来完成。那同学们可以看到在前面我们写的这一个。家庭收支。记账小软件呢,其实这里面没有用到结构体,而且大家有没有发现这个代码的维护性是比是比较差的,为什么呢?你看我们代码呢,没有使用到函数,都是一堆一堆往下写,你看这边开开了三这样去写。你看这个代码其实看起来是非常糟糕的,对不对,说它没有结构体,没有结构体,而且呢也没有用函数,这样是肯定阅读性不好,而且可维护性很差,所以说我们现在呢是这样子的。就是前面使用什么呢,结构体来完成,并且。并且使用函数函数来提高提高代码,或者我们这个项目啊,提高我们的提高。
01:01
来提高项目的这个模块化编程。对不对,因为你现在想一想,你目前的代码都是。比如说你看这点。K3就一堆代码往里面一写,可读性是比较糟糕的,现在呢,我们就要用结构体再加函数将其进行一个优化来,现在老师就要开始处理了,我们先写一个文件。新建一个项目啊,新新写一个文件哈,叫my cat。My account。二。OK,那现在呢,我们进行一个改进。进行一个改进。当然这些改进呢,并不是说要全全部重新写一遍,没,没这个必要,只是改一下而已。我们怎么改呢?我们一步步看。该引入的头文件肯定是少不了的,对不对,这这个肯定是少不了的,然后呢,我们这边需要定义一个结构体了,定义一个结构体。
02:04
对,那这个结地的我这样写是my family,我写个my family,就我家庭的一个记账系统,那这里面呢,我写几个成员呢,第一个flag。就是我现在这里面有没有这个flag,就是表示是否有至少一笔啊,至少一笔收入或者支出,是不是我们以前这样的,第二个是不是这边有我们的一个明细呀,明细肯定要封装到这里面去,Details什么呢,3000。这是不是以前这个是我们的明细。我们明细呢,放到里面去,是不是还有一个东西啊,就是我们的余额还有多少钱,Balance也放到这里面去,Balance余额就当前的余额有多少。代码就行了,那现在呢,这个做完了以后,各位同学根据我们前面写的是不是我们会用到一系列的。
03:06
一系列的这个相关的变量,这些变量呢,如果没有被封装到里面去,我们就自己拿来用好吧,这些呢,我就拿过来。当然里面有些有一些呢,我们已经封装到这里面去了,就不需要再有了,我把这个拿下来,把这些变量呢,我们做成一个全局变量。全局。I全局变量。好的,那K我们是要呃留一个对吧。K,我想一想,这个K要不要呢?先放这吧,啊,Lo lo,我们肯定是要要的,Details已经被封装到里面去了,所以这个呢,我们就不要了,好吧,这个我们就不要了。也放到。Note这个说明我们还是要要的,保留在这,Temp还需要,Balance已经封装起来,说这个呢,咱们也不要了,因为封装到这个结构体里面一个成员去了吗?Choice需要保留。
04:04
Flag也被封装了,所以说我们只需要这么几个变量就可以了。好的,放这那现在呢,全局变量有了,我们结构体也有了,下面呢,我们就来封装几个函数。首先我们看到这里,好,同学们。嗯,菜单的显示。同学们看,我们首先呢,应该把这个菜单的显示给它包起来,我们写一个函数void。没,没有。Me nu,好,这个这个函数呢,我们准备干什么呢?这个函数。该函数。专门用于专门用于显示菜单。是不是这样就比较好管理,专门用于用于显示哈,专门显示菜单也可以,你看我们在前边这个菜单的显示呢,其实是比较乱的,Do well,这这比较乱,所以现在呢,我们一系列一一次性的把这个do well整个拿过来。
05:08
大家看清楚了,我从这开始一一大堆拿过来了啊,这一大堆,包括这个Y循环,我们都把它包进去。包到我们的,相当于说整个这一块,这一大块,我们全部拿到我们这一个。这个函数里面去,那当然了,待会肯定有些要裁剪的,往这往这一放,往这一放过后,我们看哪些需要拿掉哈,来一步步的走,不着急。好,这是这个呢,是专门用于显示菜单的。那显示菜单哪些地方需要处理呢?首先。这个flag是从一个结构体传过来的,所以这边呢,我们要接收一个结构体。就是你这个。这个账账号啊,账户结构体,我们拿到my family,看我怎么封装的哈,一步步来my family,然后呢,这边。
06:06
我们用一个结构体的D指针来传递就更方便了,我们取个名字就叫my b account,没问题吧,把这个大写的M改一下,我们接收他,那接收它下面哪些可以改呢?好,嗯,我们一步步来,首先首先我们看到这个flag就要从这面去就可以了。是不是从这个结构体里面去,所以说我把它换一下。诶,这个地方我我们想一想。嗯,到时这个这个整个封装成一个函数吧。好吧,这个倒时间整个封装成一个函数,所以说待会儿这个我们我们就把这个先先去掉,先写一个。好,我先暂停到这里。这个先写了,这边是不是倒时间,我们也把它封装成一个函数,这个能理解吧,倒时间我们也把它封装成一个函数。
07:03
IF。YY。对,到时间这个第三项呢,我们整个从这也把它封装成一个函数,能理解吧,就到我们这边全部都是一堆函数了,管理起来就非常的方便,这又是一个函数print。ZZ。好,上面呢,少了一个分号,确定是否退出这个地方,我们也把它封装成一个函数。对,那到时间其实就是几个函数的事了。对,这边就是也是一个函数PF。跑起来。就是KK,那同学们看胡硕老师你在写什么东西,好像看不太懂,大家看我将来这个菜单。我这个菜单呢。就是我这个菜单,它的作用就是去显示菜单里面该做什么事情,全部用我们相关的函数来调用就简单了,那如果这样写完了过后,大家知道我的主函数应该怎么写吗?
08:04
我的主函数就需要做这一件事情就可以了,我的主函数就这么去写。Me?Me,那么这边我怎么写呢?首先我创建。创建一个结构体变量。是不是结构体变量,我们这个结构体变量是不是就是老师在这定好这个东西啊,我们拿一个过来。创建起来,对,前面应该有一个structure。别忘了。到这边呢,我们定义它的一个变量名,就小写的M就可以。对,那这个时候,呃,这个结构体变量有了过后,是不是我们要初始化一下,初始化。出。初始化。那么初始化哪些东西呢?无所谓,就这些值吗?Flag flag,默认是不是我们是嗯,零了,还记得吗?那就这样写了,我们my family。
09:02
My family初始化想它的flag。默认等于零,没有问题吧,同学们,那么还有my family什么信息呢,点?对他的balance,他balance是不是我们以前默认是1000块钱是不是也没问题吧。好,还需要最关键就是要去初始化它的details,那么它的details我们怎么去初始化呢?也很简单点,Details。你原先怎么给的值,现在照原先的方式给他就可以了。是不是,呃。这个地方呢,有一个细节。这边有个细节就是。我们看一下。呃,这个地方应该怎么给他哈。给他,那如果是按照以前这个方式的话呢,实际上是这样给的。是不是这样给,但是你会发现这样给呢,可能会不行啊,为什么不行,我们解释一下,看我直接给。
10:07
我这样给呢,你看他是要报错的。为什么报错呢?因为你这个details啊,它是一个。产量是不能够是不能够直接给赋值的,所以说我们这边要换一个方案,怎么方案呢?就是用拷贝的方式赋值。对,这个地方需要使用拷贝的方式复制。OK,那怎么拷贝的方式呢?首先我用一个member set先清一下零,哎,来走一个哈,来my family。这个地方稍微有一点点绕,我们找到my family的这个details,然后呢,我要对它进行一个处理,怎么处理呢,我要拿到3000。个自己。啊,3000个字,因为是3000呢,因为你给的就3000嘛,差嘛,然后呢,零这个就清零。
11:04
啊,第一个我们要清零,清零完了过后我们再去拷贝就完事了,使劲copy。这个这个函数还记得吗?使string copy,我要往哪里面copy呢?向这个地方。像我们这一个成员变量拷贝一个信息,就是同学们看到的这一堆信息。因为不能直接复制,对不能直接复制,我就拷贝过去,这是可以的,好,这个拷贝完了过后,这个代码就不要了。大家看懂了没有?拷贝过去。那也就是说现在呢,我们这三个都已经初始化了,如果初始化完了过后就调用,调用哪一个函数呢?调用这个M,呃,Me me u显示菜单。显示菜单。这个同学们现在慢慢理解哈,就说我为什么这么去做呢?是因为我想用结构体和函数的形式来完成,不然的话呢,我这个代码就看起来很乱。
12:06
现在你看我初始化一个结构体,再调用我们这个菜单,这个菜单这块就OK了。看到没有,调一个函数就完事了,那么在这个函数的时候呢,我们需要把这个结构体传进去,传的时候要用地址的方式传递,为什么是地址呢?因为我这一个。专门显示菜单的函数要接收一个结构体,我不希望只拷贝,所以说我用指针来接收的,那现在这个就OK了,你看XYYZZ,这个就表示去显示收支,这个就表示要去收,登记收入,这个表示要登记支出,这个表示退出,代码就写完,那么我们可以试一下,看看目前这个菜单是否。已经可以使用了,好不好?来吧,我们先申请一下这个解决方案。先生,请一下这个解决方案,下一步同学们知道老师要怎么做吗?其实就是要把这个XYZKK换成函数就完事了。
13:07
就这是待会儿要做的事情。好,我们看一下代码呢,是否生成好了,好像是有错误是吧。啊,成功了,成功了过后呢,我们来运行一下。看菜单是不是又出来了,输个一。X2。三。是是不是好,那现在呢,我们要做的事情就是把这四个功能分别用函数的形式来体现,这个是显示菜单完成了,现在呢,我们来完成下一个就是登记一笔收入。登记一笔收入啊,或者叫支出都行,我们来登记是完成。完成一个登记。登记什么呢?登记收,呃,登记支出吧,登记支出,那我就开始写一个函数了,Void配,比如说我这个函数叫配,那配的时候呢,你仍然把这一个结构体给我,因为我需要对你这个结构体进行操作嘛,这个大家看看能否理解,其实就是用函数把它包起来,那你这边再去需要重写吗?不需要重写,你只需要把老师前面写的这一个支出的这一个这段代码从这开始看到啊,看清楚。
14:23
看清楚整个从这里拷贝到这边来就可以了。然后呢,把这边做相应的变化即可。是不是它提示输入该balance肯定不让解写了,因为为什么呢,你这个balance啊,呃是在这里面,所以说你要这么去取了,来同学们看。是不是你的balance是存在我们这个结构体里面的,包起来点一下就可以。是不是?Break肯定不是break了,因为以前是已经是函数了,既然你是函数,显然就不用break,而是return。理解了吧,因为你像是函数的调用,不再是一个Switch的调用了,下面这个呢,Balance也是一样的。
15:04
哎,这个balance也是一样的,这样去处理。好,下面这个呢,一样的,是不是也是这样去处理啊。Balance拿到了。可以的,Details是不是也是这样处理啊?Details我们先拿到这个结构体。点。Details是不是就可以了,然后这个flag是不是也是一样的。Flag呢,是属于我们这里这个一个成员成员了,好,这个支出我们就写完了,有支出是不是,我们紧接着再来写一个收支明细,我们可就可以验证了呀,来我们写一个收支明细看一下。看看我们这段代码是否是OK的,那这个地方怎么调呢?因为你现在已经是支出,支出的话是三,所以说把这个地方就直接用一个配来调用就可以了,传入一个什么呢?OK,传入。
16:01
这个就可以了。看到没有,因为这个已经是指针了,所以说传的也是本身就是指针,在这个地方传的my family,就是这边接收到my family account就是一个指针,所以说这个支出就完成了,那下面呢,我们把这个收入也给他一并写了,好吧,其实大同小异,我们在使用函数,诶使用函数完成什么呢?完成登记什么呀。登记一个收入。那登记收入呢?老师就这样写income。同样的道理,我们也接收到这个结构体,看到没有,整个过程其实就是在对结构体进行一个操作,那现在呢,也不需要重写,我们只需要在这里找到这一个登记。收入的这段代码拿过来封装到我们这个函数中,大家看,大家现在是不是一直感觉到老师在不停的封装啊,就是封装函数的作用,就是搞这个封装和复用,好我把这个呢格式化一下。
17:04
对,可是化这地方该改的地方就改一下就可以了,好,这边呢。Balance就应该这么去取了。包起来。连一个balance。没问题,同学们点balance好的。那下面这个note note这个地方也要用这种方式来获取到balance。这个details。是不是也要这样去处理一下?最后这个flex是不是也要这么去处理一下。Flag就写完了,好,这个就是我们的一笔叫做登记收入就写完。那登记收入写完,是不是我们在这个地方直接调用这个income就完事了,看这就是所谓的一种模块化编程。是不是还有一个显示明细啊,显示明细就更简单了,老师呢,再来使用一个函数。使用函数干什么呢?显示明细。
18:01
显示明细。那这个地方我们就直接写这一个show dear void。Show。Details,跟着老师思路好,同样我们也接收到这一个结构体的指针。那这里面我们怎么去封装呢?还是老规矩,找到这段代码。是不是找到最终代码把这个扔进去。扔进去过后呢,我们稍微的处理一下这个flag,显然要从我们这个结构体里面获取。能理解,好把它包起来。包起来过后呢,这边来一个flag。没问题吧,下面这个details也是一样。包起来,把这个details打出来一下就可以了。Detail。好,这个代码呢,就写完了。写完了过后,我们显示的时候呢,仍然是在这个位置显示受。在哪寝室呢?
19:00
哎,调这是吧,显示明细,这是显示明细的地方嘛,然后把这个MY。Family count放进去,这就是用来显示明细的。又写完了,还剩最后一个。还剩最后一个就是一个退出,好,退出我们待会儿我们先看一下现在能不能用,再完成退出,好吧,跑起来。我们现在看一下,此时此刻我们这个封装的过程是不是已经可以用了,来玩一把。来玩一把。现在呢,我们首先登记一笔收入好。我们先看明细。没问题。登记一个收入吧,呃,100块干什么呢,工资。工资是。好看一下。是不是有工资了,在登记里支出三支出,比如说十块钱干什么呢?购物。购物回车,我们再来看一下收支明细是不是也有了?没问题吧,啊完全的正确,那现在退出没有处理,所以说现在看不到,我们先把这个退出再处理一下,退出呢,我们也可以封装到一个函数中。
20:09
对,还是使用函数完成退出,大家知道老师要怎么写了吧,你看也就是说我们把这个退出这一块,这一块的功能,整个这块功能。包到一个函数中。那么大家看,嗯,这一段功能其实我们就叫MY。退出好吧,或者叫exit。这样就可以了。那么把这个代码呢,包起来。打开。各位同学,我们看这里面呢,好像没有使用到这里面呢,没有使用到我们这个结构体,因此呢,你没有必要诶写错了格式化这个地方,你就没有必要再传一个结构体进去,你只需要简简单单的在这调一下就可以了,在这调了找到这里。把这个东西直接换成函数代码就写完了。所以你看最后我们就其实就是一个main main u这个函数里面调用了另外四个函数完事了。
21:07
从逻辑上来说呢,更清晰,它变成这样一个结构了,说我们这有一个函数就是me。没有。没有啊。啊,就是我们没没用。那在这个总函数里面,我们调的是这个菜单me nu。在这里面呢,在这个函数里面,我们调用了第一个函数,两个函数,三个函数,四个函数,而这四个函数呢,就是模块化的,如果哪个地方需要增加功能,我们只需要去找到对应的函数写代码就可以了,比如说我要增加一个功能,我写我就找到对应的函数往里面想写代码就行了,而不是像我们原先这这个逻辑,呃,整个都是一坨。那你想想,你将来这个扩展性可读性其实是比较差的,好,我们来试一下,看看退出是否也可以使用了。运行之。
22:02
我们运行一下。对,运行。诶,这个有问题哈,看代码是不是哪个地方出失败了。好,我们可以看到这个退出呢,还不能这样取名,因为这个退出名字啊,叫做exit,这个函数呢,本身系统就有说说冲突了,我们得换一个叫my exit,因为系统上也有一个exit的函数,所以说就冲突了,那下面呢,我把这个名字换一下。叫MYEX,这样就不冲突运行。对,这次呢,我们看一下效果好吧。这次应该是没有什么问题。好,各位同学,你看我退出是。对不对,我输一个N,他又不退出了。是不是又打菜单我再退出,我输一个P,他说你输错了,我输一个Y退出来了。对不对,好同学们,那这样子呢,我们相当于说my account2就使用到了一个结构体加函数的形式来完成我的项目,那么这里呢,通过这样一个方式呢,我们就。
23:10
提高了。项目的模块化编程,利于将来的扩展,利于利于今后后面啊,今后今后。今今后项目项目的一个维护和扩展。是不是这个道理啊,同学们好,同学们,那关于我们第一个小项目家庭数字软件就说到这儿,我们把代码呢给大家整理一下,好来看一下。我们看看我们完成了哪些功能,那首先呢,我们来一个分页符,这就是项目。是不是我们这块讲的是项目呀,诶写错了,那项目呢,我们第一个先给各位同学讲的是哪个项目呢?第一个项目是,嗯,就是家庭收支,家庭收支记账软件这个项目。
24:00
放到这儿来吧。梳理一下。这个项目。是这样子的吧,那这个项目呢,我们要完成的功能,其实基本的功能是这样子的。放这。那这个这个功能里面包含哪些功能呢?我们简单的梳理一下,我们完成了哪些功能,从这开始走哈,我每个截个图就行了。第一个呢,首先我们有一个菜单。对不对,首先这是它的一个菜单,我们要显示出来。小字菜单。菜单显示。诶,这个菜。菜单显示对不对。菜显示菜显示就是这个小界面菜单显示,我完了过后是不是我们还有一个功能是用来登记收入啊。诶,登记收入我们也把列到这来登记收入,那登记收入这个界面呢,其实就是这个界面。是这个功能,就是我可以登记一笔收入。
25:02
也放在这了,这是这个功能,那紧接着我们是不是还有一个功能,就是登记之初。诶,想登记支出。对登记支出。那登记出租过后呢,还可以显示明细。对,有个显示明细这个功能。没问题吧,然后还有一个什么呢,退出,退出系统这边给出相应的提示,对好,那这个地方我们就一个个截了登记之初。是这个界面对吧。这是登记支出的一个界面。放这来。然后呢,显示明细,显示明细呢,其实就是这个界面,我们可以把。整个这个明细看到这里面呢,需要相应的这个对齐。还有一个退出这个系统对不对,退出系统呢,我们这有相应的提示说你是否真的要退出有一个确认。
26:03
好,这是退出系统。那这个就说完,说完过后有一点呢,就是给他说一下,我们这个版本呢,实际上是经过了好几个流程的这个项目的改进,项目改进呢,其实我们写了相当于说写了两个版本。需要两个版本,这这两个版本呢,我给他列到这里来好。项目的改进也在这儿写出来,项目改进呢,我们实际上是嗯,经历过这样几个过程。所以说有两个版本。我把代码都写到这,最后这个代码。最后实现的代码。实现代码一第一个版本是什么呢?就是相当于是呃,一个流程,就是一个没有使用。第一个版本是没有使用结构体和函数封装的,是不是这个版本版本一。代码。对,版本一。版本一呢,我们是做的这个版本,那么代码我给大家直接扔过来好吧。
27:03
代码指引扔过来在哪里呢?就在这个地方。给大家处理一下。保存好,这是我们的第一个版本的代码。对,那么第二个版本呢,我们是在这个基础上做了一个扩展,是什么呢?就是我们使用的结构体和函数进行一个模块化的处理。我同样在这拿过来就第二个版本,所以同学们呢,你你们想想是不是第二个版本应该更好一些,对吧,至少从扩展性来说要好很多,第二个版本实现了第二个版本。第二个版本呢,就是用使用了结构体加函数封装来提高。诶提高代码代码或者叫软件哈,软件模块模块化编程。啊,便于便于什么呢?便于维护。
28:01
便于维护好,这是又一个版本,那这个版本的代码呢,我也给大家板书到这边来,就是我们的my count2。大家要认真的去体会,尤其是我们初学者哈,刚开始用的时候你感觉不习惯,慢慢慢慢大家就会变得越来越清楚,代码并不是很难的,说白了说白了就是在这个命命名右里面呢,调用四个函数嘛,这个其实连连这个流程图就不需要给你们画就能看,讲的很清楚,没什么难度的,说白了他这个示意图呢,如果说一定要画的话,就是这样子一个流程。啊,它是这样子的,我给大家简单画一下哈,原画这是我们的一个主函数,这个主函数里边呢,对,我们试一下,在这个主函数里边呢,各位同学,这面有个main。有个妹没用。Me nu。这个呢是一个函数。对,在这个函数里面呢,诶,这是一个函数,这个函数分别调用了,诶,它调用了四个函数。
29:06
哪四个函数呢?我们可以简单的回顾一下,一个是呃,显示细节show detail。在看书。还有呢,这是第一个函数,还有一个incoming,就是登记,还有一个pay。是不是就是支出,还有一个是my exit。那么这四个函数呢,咱们可以认为是分别分开写的,比如说这是我们的第一个函数,那么在这里呢,它会去调用它,它去引用到这个是吧。对,或者你把这个线反反过来拉也是可以的,说老师我调用呢,我可不可以这样画,就是我把这个函数拿到我这边来用可以的。啊是一个亿四个亿,那么这边呢,又有一个函数。对,又有一个函数,这个函数呢,是我们的incoming函数,也被我们使用到。对吧,当然还有一个函数,就是配。
30:03
配函数,配函数呢也被我们使用到。对不对,还有一个什么函数呢?还有一个函数就是我们的my exit退出也被我们使用到。那这样子大家可以看到,如果将来我们要去扩展的话呢,就在各自的函数进行一个修改,比如说我将来想在这个显示,显示这个细节上做一些修改,我就改这里,如果将来呢,我要对这个incoming做一些修改,我就修改这个函数,如果将来我要在支出做一些修改,我就改这,如果我要在退出再改一个流程,我就改这很简单,比如说打个比方,我们在进行这个收入的时候呢。在进行这个收入的时候,我们有一个判断。对不对,比如说有个判断,诶,你这个收入的时候,假设是一个是一个负数,我就提示你。这个金额不对,那你怎么写呢?在这加一个逻辑判断就行了,比如说在这里我们找到这段代码。
31:03
是吧,我们这判断一下你的这个money是不是负数,然后给出提示就完了,所以说这样子呢,从理论上来说,我们维护代码其实更方便了,其实更方便,好我把这个示意图呢给大家拿过来哈。这是我们的一个示意图。帮助同学们理解的一个示意图。好,我放到这里了。是不是OK?示意图就是程序的。写到这呢?诶,为什么这样吵啊?程序。程序的一个结构示意图。结构示意图好,我放到这里了,大家应该一目了然。各位同学关于我们第一个项目家庭收支软件的,呃,分析还有实现,就给大家讲解到这里,大家最好把这个代码自己重新写一遍,加深对它的理解。
我来说两句