Android串連網路異常:android.os.NetworkOnMainThreadException

來源:互聯網
上載者:User

標籤:android   networkonmainthreadexception   串連網路異常   

package com.ccl.getimage;import java.io.InputStream;import java.net.HttpURLConnection;import java.net.URL;import android.app.Activity;import android.graphics.Bitmap;import android.graphics.BitmapFactory;import android.os.Bundle;import android.text.TextUtils;import android.view.View;import android.widget.EditText;import android.widget.ImageView;import android.widget.Toast;public class MainActivity extends Activity {private EditText et_path;private ImageView iv;@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);et_path = (EditText) findViewById(R.id.et_path);iv = (ImageView) findViewById(R.id.iv);}public void getImage(View view){String path = et_path.getText().toString().trim();if(TextUtils.isEmpty(path)){Toast.makeText(this, "地址不可為空", 0).show();return;}try {URL url = new URL(path);HttpURLConnection conn = (HttpURLConnection) url.openConnection();conn.setRequestMethod("GET");conn.setReadTimeout(5000);System.out.println("響應碼是--"+conn.getResponseCode());if(conn.getResponseCode()==200){//擷取伺服器返回的流資料InputStream in = conn.getInputStream();//將返回的流資料解析成圖片Bitmap bitmap = BitmapFactory.decodeStream(in);//顯示圖片iv.setImageBitmap(bitmap);in.close();}} catch (Exception e) {e.printStackTrace();}}}

Android模擬器版本4.1.2

異常解釋:在主線程中的網路異常

原因:Android2.3版本後不允許在主線程中直接請求網路擷取資料

解決方案(兩種):

一:onCreate方法中加入如下代碼(不推薦使用,有可能阻塞Android主線程)

if (android.os.Build.VERSION.SDK_INT > 9) {    StrictMode.ThreadPolicy policy = new StrictMode.ThreadPolicy.Builder().permitAll().build();    StrictMode.setThreadPolicy(policy);}


二:使用Android 的handler機制,另外開啟一個子線程請求網路擷取資料(推薦使用)

package com.ccl.getimage;import java.io.InputStream;import java.net.HttpURLConnection;import java.net.URL;import android.app.Activity;import android.graphics.Bitmap;import android.graphics.BitmapFactory;import android.os.Bundle;import android.os.Handler;import android.os.Message;import android.text.TextUtils;import android.view.View;import android.widget.EditText;import android.widget.ImageView;import android.widget.Toast;public class MainActivity extends Activity {private EditText et_path;private ImageView iv;private String path;//使用Handler更新主線程(UI線程)private Handler handler = new Handler(){public void handleMessage(Message msg) {Bitmap bitmap = (Bitmap) msg.obj;iv.setImageBitmap(bitmap);};};@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);et_path = (EditText) findViewById(R.id.et_path);iv = (ImageView) findViewById(R.id.iv);}public void getImage(View view){path = et_path.getText().toString().trim();if(TextUtils.isEmpty(path)){Toast.makeText(this, "地址不可為空", 0).show();return;}new Thread(){public void run(){try {URL url = new URL(path);HttpURLConnection conn = (HttpURLConnection) url.openConnection();        conn.setRequestMethod("GET");        conn.setReadTimeout(5000);System.out.println("響應碼是--"+conn.getResponseCode());if(conn.getResponseCode()==200){//擷取伺服器返回的流資料InputStream in = conn.getInputStream();//將返回的流資料解析成圖片Bitmap bitmap = BitmapFactory.decodeStream(in);//使用handler傳遞訊息Message msg = Message.obtain();msg.obj = bitmap;//傳遞的資料handler.sendMessage(msg);in.close();}} catch (Exception e) {e.printStackTrace();}}}.start();}}

注意兩點:

Message對象的建立使用obtain方法可以達到對象重用的目的,節省記憶體開銷。

Message對象可以使用msg.what = 傳遞訊息的類型,handler可以根據傳遞的訊息類型做不同處理,最佳化代碼如下:

package com.ccl.getimage;import java.io.InputStream;import java.net.HttpURLConnection;import java.net.URL;import android.app.Activity;import android.graphics.Bitmap;import android.graphics.BitmapFactory;import android.os.Bundle;import android.os.Handler;import android.os.Message;import android.text.TextUtils;import android.view.View;import android.widget.EditText;import android.widget.ImageView;import android.widget.Toast;public class MainActivity extends Activity {protected static final int SUCCESS = 0;protected static final int ERROR = 1;protected static final int NETWORK_ERROR = 2;private EditText et_path;private ImageView iv;private String path;//使用Handler更新主線程(UI線程)private Handler handler = new Handler(){public void handleMessage(Message msg) {switch (msg.what) {case SUCCESS:Bitmap bitmap = (Bitmap) msg.obj;iv.setImageBitmap(bitmap);break;case ERROR:Toast.makeText(MainActivity.this, "擷取圖片失敗", 0).show();break;case NETWORK_ERROR:Toast.makeText(MainActivity.this, "串連網路失敗", 0).show();break;}};};@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);et_path = (EditText) findViewById(R.id.et_path);iv = (ImageView) findViewById(R.id.iv);}public void getImage(View view){path = et_path.getText().toString().trim();if(TextUtils.isEmpty(path)){Toast.makeText(this, "地址不可為空", 0).show();return;}new Thread(){public void run(){try {URL url = new URL(path);HttpURLConnection conn = (HttpURLConnection) url.openConnection();        conn.setRequestMethod("GET");        conn.setReadTimeout(5000);System.out.println("響應碼是--"+conn.getResponseCode());if(conn.getResponseCode()==200){//擷取伺服器返回的流資料InputStream in = conn.getInputStream();//將返回的流資料解析成圖片Bitmap bitmap = BitmapFactory.decodeStream(in);//使用handler傳遞訊息Message msg = Message.obtain();msg.obj = bitmap;//傳遞的資料msg.what = SUCCESS;//傳遞的訊息類型,handler可根據訊息類型做不同處理handler.sendMessage(msg);in.close();}else{Message msg = Message.obtain();msg.what = ERROR;handler.sendMessage(msg);}} catch (Exception e) {Message msg = Message.obtain();msg.what = NETWORK_ERROR;handler.sendMessage(msg);e.printStackTrace();}}}.start();}}

本文出自 “Android開發學習筆記” 部落格,請務必保留此出處http://282845781.blog.51cto.com/7152559/1748797

Android串連網路異常:android.os.NetworkOnMainThreadException

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.