• MVC->MVP->MVVM架构完整演变过程剖析


    在之前对于MVP这种架构风格已经进行了深入的学习了,接下来则打算学习一下MVVM这种架构,MVC、MVP、MVVM这三者基本上会被人一起问到的,而对于MVVM,google官方推出了一个dataBinding的MVVM的框架,而从学习的角度直接上框架并非是一个非常好的学习方式,所以这次就手把手的一步步通过一个小案例来实现MVVM框架,对其原理有一个本质的了解,这样在下一次学习dataBinding时也能做到心中有数。

    MVC:

    思想:

    架构理解:

    对于上图的理解,简单描述整个过程就是用户触发了View的一个事件,然后则会转到Controller中进行处理,而它又会去操作Model,最终Model处理完了会更新到UI上来。这里用一个伪代码来模拟一下这个过程:

    而其实有些MVC会是这样的一个关系:

    具体实现:

    接下来则回到Android的代码上来,先来简单搭个框架:

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:tools="http://schemas.android.com/tools"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical"
        tools:context=".MainActivity">
    
        <EditText
            android:id="@+id/et_data1"
            android:layout_width="match_parent"
            android:layout_height="wrap_content" />
    
        <EditText
            android:id="@+id/et_data2"
            android:layout_width="match_parent"
            android:layout_height="wrap_content" />
    
        <Button
            android:id="@+id/btn_save"
            android:layout_width="100dp"
            android:layout_height="wrap_content"
            android:text="save" />
    
    </LinearLayout>

    没啥好解释的,默认Android的这个代码框架就属于MVC风格的,这个都耳熟能详了,这里还是啰嗦一下:对于V来说就是我们的布局文件,而M则是DateCenter这个类,而C则是MainActivity。那为啥会出现MVP、MVVM这种新的框架出来呢?因为目前MVC框架中的Activity太重了,跟M和V都进行耦合在一块了,所以MVP出现了。

    MVP:

    思想:

    架构理解:

    其中可以看到跟MVC中最大的区别在于MVP的Model和View之间没有引用了,然后之前的Controller变成了Presenter了。

    具体实现:

    接下来咱们来将它改造成MVP,首先先来新建一个P:

    然后它会操作Model,所以这里将这个代码牵移到P中:

    此时Activity调整为:

    此时一个基本的MVP就出现了,其中“View跟Controller给拆开了,并提取出了一个Presenter”,目前这个基本的MVP框架中P是直接持有了具体Activity的引用,然后目的是用来调用它里面的刷新界面的方法:

     

    很明显对于P来说不需要用到MainActivity中的所有信息,只需要知道这个界面是如何更新UI的就行了,所以直接持有Activity的引用设计不是太合理,面向接口编程是最提倡的,也就是能只获取最小的信息则就获取最小的,这样会解耦,所以咱们将其抽象成一个接口,里面会存放各个跟UI相关的操作接口:

    思考:在上面中加粗了一句话“View跟Controller给拆开了,并提取出了一个Presenter”,那能否不提一个Presenter,而达到同样的效果呢?其实是可以的,而这种写法在实际工作中也是很频繁的,下面改装一下,这里先将建几个包将其分开一下:

    而这里则对MvcActivity传统的写法进行调整一下:

    怎么能让控件层与View之间耦合不那么紧呢?其实就是想办法把这段代码给去掉:

    其实就是将这个设置封装到View里面既可:

    package com.android.mvc_mvp_mvvm_demo.mvc;
    
    import android.content.Context;
    import android.util.AttributeSet;
    import android.widget.EditText;
    import android.widget.LinearLayout;
    
    import androidx.annotation.Nullable;
    
    import com.android.mvc_mvp_mvvm_demo.R;
    
    public class DataView extends LinearLayout {
    
        private EditText et_data1;
        private EditText et_data2;
    
        public DataView(Context context) {
            super(context);
        }
    
        public DataView(Context context, @Nullable AttributeSet attrs) {
            super(context, attrs);
        }
    
        public DataView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
            super(context, attrs, defStyleAttr);
        }
    
        public void showData(String[] data) {
            et_data1.setText(data[0]);
            et_data2.setText(data[1]);
        }
    
        @Override
        protected void onFinishInflate() {
            super.onFinishInflate();
            et_data1 = findViewById(R.id.et_data1);
            et_data2 = findViewById(R.id.et_data2);
        }
    }

    为啥要改上面这种比较简单的代码呢?其实这里是要来对于很多人都说的:“MVP要比MVC要好,MVC的View和Controller都混到一块”这样的观点持怀疑态度,很明显通过上面的这样改良,也没有提取出一个P,跟MVP的效果差不多呀, 那为啥要说MVP比MVC要好呢?可能有些人会说MVP不是会提取出一个View的接口嘛,那对于上面改良的这种代码也可以提取呀,下面试一下:

    所以其实对于MVC和MVP框架本质来说其实是一样的,当然细节会有不同,这种观点其实没必要较真,只是为了了解其了本质才这样挖掘的,而平常在讨论这俩框架的区别时,还是可以说:“Android自带的框架就是MVC,而抽出来一个P层的则是MVP”。

    MVVM:

    接下来则来看最后一种架构了,这种目前还木有在真实项目中用过,但是对于它的了解也早就有所耳闻,相比MVP而言,它的数据如果发生变化了会立马反馈到UI上,而不需要通过回调通知UI进行刷新,反过来如果UI更新了数据状态也会自动到去将Model中的数据给自动更新 。

    思想:

    具体实现:

    先来新建一个ViewModel:

    此时Activity就可以这样来调用了:

     

    接下来要实现数据自动显示在界面上该如何修改呢?怎么明显Activity跟ViewModel需要进行绑定才行,所以新建一个类:

    在这里面则需要监听textView和text的变化,对于TextView的变化监听有现成的API这个不用操心,但是对于第二个参数text很显然不能,所以此时我们得将ViewModel中的这块得封装一下才行:

    具体修改如下:

    此时回到ViewBinder类中:

    哦,原来双向绑定的核心是这么搞的,就是哪方改变了再通知另一方,好接下来咱们再回到ViewModel中:

     接下来则可以进行Activity与ViewModel的绑定了,先来在ViewModel定义一个绑定接口供Activity来调用:

    好,接下来调用一下:

    至此一个简单的MVVM框架就搭建完了,说实话还是有些麻烦的,不过好在Google针对MVVM推出了成熟的框架,如开篇有说,DataBinding,商用的话基本上会基于这个框架来进行MVVM的开发,这次对于MVVM的核心原理了解了之后,下一次就准备来学习一下DataBinding框架的使用及原理啦。

  • 相关阅读:
    JavaScript 类私有方法的实现
    sublime小程序插件
    显示引擎innodb状态详解
    JAVA学习资料大全
    mongo-aggregate命令详解
    PHP error_reporting
    mongo基本命令
    php56升级后php7 mcrypt_encrypt 报错
    docker 基础命令
    敏捷建模:增强沟通和理解
  • 原文地址:https://www.cnblogs.com/webor2006/p/12463543.html
Copyright © 2020-2023  润新知