零、前言
Spring + Angular 前后端分离开发已经学了三个月,深感其难度较高...尤其是在初学时不知道为什么要追求前后端分离。本文是我从最初开始接触软件到现在为止,对于面向对象、MVC和前后台分离的一些理解。
在发现新事物时,人们往往不愿意接受新的事物,可后来逐渐适应了、发现了它的优点之后,却又离不开了...
一、“混沌无序”——MVC不分离
早期的软件是面向过程编写的,换句话说,这样的软件就像一座加工厂、流程图,它只是把现实生活中的某种流程改编成代码,让计算机去处理罢了。
(为了专注于思考问题本身,本文没有代码)
上面的图片只是抽象成普遍性的流程,可实际上呢?
如果用PHP和Html来编写一个简单的学生管理页面,不进行MVC分离,会怎么样呢?
就像这样,这样的程序中,代码的执行逻辑和思维的逻辑是完全一致的,也就说,逻辑想到哪,代码就可以写到哪,想在这个时候查数据库,就直接把SQL语句写进去,想加样式,就在Html标签里面添加class。
可是这样的代码,耦合度非常高,由于逻辑层、数据层、界面层全都混杂在一起,甚至会经常出现Html、JS和PHP混写的情况,这就需要开发人员同时掌握前端和后端的语言;
同时,由于各层代码混在一起,会导致每个功能的代码都会非常长,维护十分困难,每次维护之前必须要在大脑里复现编写时的流程,才能对代码进行修改,往往根本想不起当时的代码在写什么,很难下手。
二、“黎明初晓”——MVC分离
由于MVC不分离的开发有以上的诸多缺点,MVC分离的思想出现了,并且出现了许多框架,比如ThinkPHP就是MVC分离的PHP框架。
在ThinkPHP中,
M指Model,模型。M层定义了对象的属性和方法,供C层去调用,并且M层承担起了和数据库数据交换的任务;
C层是Controller,控制器。负责数据转发,C层注重软件的业务逻辑,但不去关心某个业务逻辑是怎样实现的。
(例如,C层就像一个组长,它让M层的小明去完成一项任务,但并不关心这项任务是怎么实现的,因为实现方式是M层该负责的事情)
V层是View,视图,也就是界面。V层负责把数据和界面打包在一起,渲染成最后的页面,然后交给C层,由C层返回给用户。
那么,如果把刚才的学生管理界面改写成MVC分离的思维,会怎么样呢?
MVC分离的思想更面向对象——它更专注于不同层之间的关系,而不是非和大脑中的思维顺序保持一致,换句话说,如果把各层的代码首尾相接,它是不能直接按前后顺序去运行的,因为各层之间的代码是调用的关系,而不是前后顺序的关系。面向对象打破了面向过程的那种“加工厂”型的顺序思维。
MVC分离的意义,在于把数据层和界面层从业务逻辑中抽离出来,使得在编写每一层的时候只需要考虑本层负责的内容,而不用全面考虑,大大降低了思维量。在修改时,也只需要考虑所修改的这部分,而不用全局考虑。
可是这样还是有一些问题没有解决,简单的说,还是“分离”的程度还不够。
我们知道,后端工程师往往不擅长UI的设计,前端工程师往往不擅长数据结构和算法。虽然前端的HTML、JS和后端的PHP不用像之前那样写在同一个文件里,但它毕竟还是不同语言,如果想单独的开发一部分,就比较困难,开发前端页面时必须借助后端数据,开发后端时必须必须借助前端发起请求。
三、“泾渭分明”——前后端分离
终于,富有智慧的先人们终于发明了前后端分离的思想。把客户端和服务端分离。
在前后端不分离的时候,页面和数据还是耦合的。
例如ThinkPHP的V层,只不过是一个提前写好的静态模板(就像一张没写的试卷),然后把数据填到指定的位置,再把渲染好的网页(就像一张写完的试卷,写上去的就是动态数据)返回给C层,再返回给用户浏览器。
静态网页
填好数据的网页
那么前后端分离时怎样的呢?
前端指的是运行在用户浏览器上面的程序;
后端指的是运行在服务器上面的程序。
在用户发起请求的时候,先向前台服务器请求前端程序,把所有的前端内容拷贝下来,但此时的前端不再像HTML那样仅仅是一个静态页面,而是一个也有控制器、也有模型的完整系统,它可以知道自己应该向哪个后台地址请求,以及该如何渲染前端界面。
然后紧接着,运行在浏览器的前端程序,会向后端服务器发起若干个请求,服务器返回数据之后,前端将数据填入,就得到了完整的页面,呈现给用户。
这样的好处是,如果想进行前后端分离的开发,只需要前端开发者和后端开发者制定一个协议即可(前端向哪个地址、以什么方式、请求什么资源,后端去返回对应的资源就可以了),前端开发时不需要有一个完整的后端,后端开发时也不需要完整的前端。这样就实现了“各写各的”,甚至前端不用知道后端使用什么语言去开发——他只要知道如何去请求后端就可以了;后端也不必考虑数据如何显示——只要知道前端想要什么数据就可以了。
从另一方面去考虑,这样做还有优点,还可以减小服务器压力:
在前后端不分离的时代,V层的模板渲染是由服务器完成的(服务器把HTML模板填入数据后,才能返回),这样,用户的每一次请求,既要返回数据,又要返回HTML页面和体积庞大的JS样式。
前后端分离后,第一次请求,用户把前端程序直接下载到本地,运行在本地,并且,这种前端的UI是相对固定的,不会频繁发生变化。这样,之后的每一层请求,只需要向服务器请求动态变化的数据就可以了,不必重复的加载相同的页面,减少网络带宽浪费。甚至可以直接把前端页面缓存,在一段较长的时间内,都不必再向前端发起页面的请求了。
四、总结
从最初的面向过程,到后来的面向对象,再到MVC分离,前后端分离,这应该是软件工程历史上的一次次进步,推动了软件世界的一次又一次发展。
作为普通人,我们没有能力去制定规则,但我们可以学习更先进的思想,去提高自己,用这些先进思想去辅助自己开发出更规范的产品。
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。