Android Mvc 模式

1.Mvc 介绍

   Model-View-Controller(模型-视图-控制器) 模式,这种模式用于应用程序的分层开发。
   model:模型层主要是处理数据的,主要进行网络请求,复杂的数据操作
   view:视图层xml 负责数据的显示,主要是xml负责
   controller:控制层处理用户交互的部分,负责从视图层获取数据传递给模型层进行处理activity充当这个角色

如图:

2.Android中demo

(1).代码的目录结构:

(2).model层:

public interface GetDataModelImpl {
    public void getData(String url, GetDataListener listener);
}
public class GetDataModel implements GetDataModelImpl {
    @Override
    public void getData(String url, final GetDataListener listener){
        OkHttpClient client = new OkHttpClient(
        final Request request = new Request.Builder()
                .url(url).addHeader("Content-Type","application/json")
                .build();
        client.newCall(request).enqueue(new Callback() {
            @Override
            public void onFailure(Call call, IOException e) {
                listener.onFail();
            }
​
            @Override
            public void onResponse(Call call, final Response response) throws IOException {
                final String resultStr = response.body().string();
                Handler mainHandler = new Handler(Looper.getMainLooper());
                mainHandler.post(new Runnable() {
                    @Override
                    public void run() {
                        //已在主线程中,更新UI
                        if(response.isSuccessful()){//回调的方法执行在子线程。
                            listener.onSuccess(resultStr);
                        }else{
                            listener.onFail();
                        }
                    }
                });
​
​
            }
​
​
​
        });
    }
}

(3).view层

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    >
​
    <Button
        android:id="@+id/bt0"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:text="mvc1获取数据"></Button>
    <Button
        android:id="@+id/bt1"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:text="mvc2获取数据(变相的)"></Button>
    <Button
        android:id="@+id/bt2"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:text="没有用mvc模式的"></Button>
    <TextView
        android:id="@+id/tv"
        android:layout_width="fill_parent"
        android:layout_height="fill_parent"
        android:text="返回的结果"></TextView>
​
</LinearLayout>

(4).controller层

public class MainActivity extends FragmentActivity implements GetDataListener {
    private GetDataModelImpl getDataModel;
    private Button bt0;
    private Button bt1;
    private Button bt2;
    private TextView tv;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        bt0 = (Button)findViewById(R.id.bt0);
        bt1 = (Button)findViewById(R.id.bt1);
        bt2 = (Button)findViewById(R.id.bt2);
        tv = (TextView)findViewById(R.id.tv);
​
        bt0.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                String url = "https://www.baidu.com/";
                getDataModel.getData(url,MainActivity.this);
​
            }
        });
        bt1.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                //换一种形态的mvc模式这个时候只不过是没有回调lister,但是方法返回值里面有也属于mvc模式
                int number = UtilTools.parseInt("2");
                Toast.makeText(getApplicationContext(),"获取的数据"+ number,Toast.LENGTH_LONG).show();
            }
        });
        bt2.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                //没有mvc模式 数据处理的能力都在activity层也就是Controller层
                //这样造成activity 有控制层的能力也有model层的数据处理的能力,导致activity代码量很大
                String url = "https://www.baidu.com/";
                getData(url,MainActivity.this);
            }
        });
        if(getDataModel == null){
            getDataModel = new GetDataModel();
        }
    }
​
    @Override
    public void onSuccess(String data) {
        if(!TextUtils.isEmpty(data)){
            tv.setText(data);
        }else{
            tv.setText("请求的结果为空");
        }
​
    }
​
    @Override
    public void onFail() {
        tv.setText("---请求的结果失败--");
    }
    public void getData(String url, final GetDataListener listener){
        OkHttpClient client = new OkHttpClient();
        final Request request = new Request.Builder()
                .url(url).addHeader("Content-Type","application/json")
                .build();
        client.newCall(request).enqueue(new Callback() {
            @Override
            public void onFailure(Call call, IOException e) {
                listener.onFail();
            }
​
            @Override
            public void onResponse(Call call, final Response response) throws IOException {
                final String resultStr = response.body().string();
                Handler mainHandler = new Handler(Looper.getMainLooper());
                mainHandler.post(new Runnable() {
                    @Override
                    public void run() {
                        //已在主线程中,更新UI
                        if(response.isSuccessful()){//回调的方法执行在子线程。
                            listener.onSuccess(resultStr);
                        }else{
                            listener.onFail();
                        }
                    }
                });
​
​
            }
​
​
​
        });
    }
}

(5).git 下载地址https://github.com/wyc1411162011/MvcDemo.git

3.优缺点总结:
优点:mvc采取分层结构结构清晰明了,各个层级分工明确耦合性低

缺点:(1).mvc模式activity充当view和controller这两种角色,随着项目扩大activity里面代码会很多,不适用 复杂的页面
           (2).view层和model层有交互,有代码的耦合。
           (3).model层数据操作没有和activity生命周期绑定,activity结束model数据处理还会有回调,容易引起context的内存溢出

4.问题及解答:
           (1).model层封装了一层接口为什么要用接口直接的类不是更简单吗?
           答案:个人理解这就是面向接口编程,为了以后好扩展,比如获取数据的方法变了,直接新加一个实现接口的类,在activity里面换点指向的新对象就行了,符合设计模式里面的开关原则,对内修改关闭,对外扩展开放的原则,鬼知道这个玩意以后会不会,为以后扩展留好后路。
           (2).如果请求方式从okhttp换成retifit怎么办?
            答案:网络请求,最好封装一层,在model层请求数据,不要用具体的okhttp或者retifit 用自己封装统一的请求处理,方便以后的全局替换,比如以后又有崭新的框架了。
           (3).如果有多个model怎么办 会有多个listener 逻辑处理很混乱?
           答案:这就要求listener 封装的足够通用,这个model能用,其他model也能用,项目封装几个通用的listener,让足够多的model 层使用。

猜你喜欢

转载自blog.csdn.net/u010939317/article/details/105730886