1. 程式人生 > >Android studio 封裝請求網路工具類以及實現(包含單例模式)

Android studio 封裝請求網路工具類以及實現(包含單例模式)

一般我們在請求網路資料時都會通過一個或多個連結去請求網路資料,但對於一些初學人士都只是在一個類裡或MainActivity做很多操作,這樣的話耦合度太高,程式碼感覺非常繁瑣,專案執行時可能會卡。一般在公司裡面也會要求低耦合,高類聚。這時就會通過封裝工具類來降低耦合度,這樣也就減少了程式碼與程式碼之間的繁瑣程度。

封裝好的工具類也可以直接拿過來用,不用再重寫程式碼,非常方便。

我封裝的HttpUtils網路請求工具類被我加了單例模式,單例模式你們也可以直接去了,主要就是加了單例以後多次呼叫了,詳細情況看程式碼:

1、封裝HttpUtils類

HttpUtils 類

package bawey.com.day14.utils;

import android.os.AsyncTask;

import java.io.BufferedReader;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;

public class HttpUtils {
    final private String ERROR01="請求失敗!";
    final private String ERROR02="請求異常!";

    private OnHttpUrlLisent onHttpUrlLisent;

    //單例模式
    private static HttpUtils httpUtils = new HttpUtils();
    private HttpUtils(){}

    //使本類唯一,只能允許一處執行緒進入,不允許有第二處執行緒進入
    //只能被一方呼叫,不允許第二方呼叫
    public static HttpUtils getHttpUtils(){
        if (httpUtils==null){
            httpUtils=new HttpUtils();
        }
        return httpUtils;
    }

    //封裝網路請求
    public void get(String url){
        MyAsyncTask myAsyncTask = new MyAsyncTask();
        
        //開啟AsyncTask
        
        myAsyncTask.execute(url);
    }

    //AsyncTask裡面封裝了Handler和執行緒池來實現非同步任務和執行緒間通訊
    //AsyncTask的例項必須在主執行緒中建立
    
    class MyAsyncTask extends AsyncTask<String,Void,String>{

        //用於初始化操作的方法,執行在主執行緒,可以方法在裡面列印“正在載入中……”等等操作
        //不是必須要寫的
        @Override
        protected void onPreExecute() {
            super.onPreExecute();
        }


        //AsyncTask裡面四個方法中唯一一個在子執行緒執行的方法,可執行耗時操作
        //必須重寫的方法
        @Override
        protected String doInBackground(String... strings) {
            try {
                URL url = new URL(strings[0]);
                //開啟連結
                HttpURLConnection connection= (HttpURLConnection) url.openConnection();
                //設定請求方式,可以設定GET,POST
                connection.setRequestMethod("GET");
                //設定超時,五秒內未加載出網路資料就會彈出“服務無響應”
                connection.setConnectTimeout(5000);
                //設定讀取超時,五秒內未讀取到資料就會彈出“讀取超時”
                connection.setReadTimeout(5000);
                //獲取狀態響應碼
                int code = connection.getResponseCode();
                if (code==200){
                //獲取流資料,屬於位元組流
                    InputStream inputStream = connection.getInputStream();
                    //橋轉換,將位元組流轉換成字元流
                    InputStreamReader streamReader = new InputStreamReader(inputStream);
                    //新增快取流,加快讀取速度
                    BufferedReader reader = new BufferedReader(streamReader);
                    //快取區
                    StringBuilder builder = new StringBuilder();
                    String s="";
                    while ((s=reader.readLine())!=null){
                        builder.append(s);
                    }
                    
                    //關閉資源
                    streamReader.close();
                    reader.close();

                    //返回json資料
                    return builder.toString();
                }else{
                    //放回請求失敗
                    return ERROR01;
                }
            } catch (Exception e) {
                e.printStackTrace();

                //返回請求異常
                return ERROR02;
            }
        }

        //更新進度的方法,可以次被多次呼叫,可以在這個方法中設定進度條載入
        //不是必須要寫的
        
        @Override
        protected void onProgressUpdate(Void... values) {
            super.onProgressUpdate(values);

        }


        //網路請求完返回最後結果執行的方法,s引數是doInBackground返回的請求結果
        //必須重寫的方法
        
        @Override
        protected void onPostExecute(String s) {
            super.onPostExecute(s);
            switch (s){
                case ERROR01:

                    //請求失敗時把值賦給請求失敗的監聽
                    onHttpUrlLisent.errorLoad(ERROR01);
                    break;
                    
                case ERROR02:
                
                    //請求異常時把值賦給請求失敗的監聽
                    onHttpUrlLisent.errorLoad(ERROR02);
                    break;
                default:

                    //請求成功時把請求到的String型別json資料賦給請求成功的監聽
                    onHttpUrlLisent.seccssLoad(s);
                    break;
            }
        }
    }

    //封裝監聽器
    public interface OnHttpUrlLisent{
    
        //請求成功時的監聽方法
        void seccssLoad(String json);

        //請求失敗時的監聽方法
        void errorLoad(String error);
    }

    public void setOnHttpUrlLisent(OnHttpUrlLisent onHttpUrlLisent){
        this.onHttpUrlLisent=onHttpUrlLisent;
    }


}

2、呼叫HttpUtils類

package bawey.com.day14.activity;

import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v7.app.AppCompatActivity;

import bawey.com.day14.R;


public abstract class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);  
     
        //呼叫請求網路工具類
        HttpUtils httpUtils = HttpUtils.getHttpUtils();
        
        //呼叫工具類封裝的網路請求方法-------引數是String型別的地址,我用的拼接
        httpUtils.get(HttpsConfig.URL01+HttpsConfig.URL02);

        //設定封裝的監聽,獲取請求的資料
        httpUtils.setOnHttpUrlLisent(new HttpUtils.OnHttpUrlLisent() {
            @Override
            public void seccssLoad(String json) {
            
            //列印一下資料
                Log.i(TAG, "seccssLoad: "+json);

            }

            @Override
            public void errorLoad(String error) {

                //判斷是否請求成功
                if (error!=null){
                
                    Log.i(TAG, "errorLoad: "+error);
                    
                }else{
                
                    Log.i(TAG, "請求成功!");
                    
                }

            }
        });
    }
}

從上面程式碼可以看出,在一個MainActivity主方法裡面是不是減少了很多程式碼啊!是不是感覺很方便。

3、檢視列印的結果,是不是請求資料已經出來了啊!說明工具類可用。
在這裡插入圖片描述

初次涉入部落格,如果喜歡我寫的部落格的話就關注一下我吧!往後還會有更多程式碼更新!謝謝各位了!
如果我的部落格有不足的地方,還請個位大牛指點指點!