『壹』 android 大量多線程怎麼優化
在程序開發的實踐當中,為了讓程序表現得更加流暢,我們肯定會需要使用到多線程來提升程序的並發執行性能。但是編寫多線程並發的代碼一直以來都是一個相對棘手的問題,所以想要獲得更佳的程序性能,我們非常有必要掌握多線程並發編程的基礎技能。
眾所周知,Android 程序的大多數代碼操作都必須執行在主線程,例如系統事件(例如設備屏幕發生旋轉),輸入事件(例如用戶點擊滑動等),程序回調服務,UI 繪制以及鬧鍾事件等等。那麼我們在上述事件或者方法中插入的代碼也將執行在主線程。
一旦我們在主線程裡面添加了操作復雜的代碼,這些代碼就很可能阻礙主線程去響應點擊/滑動事件,阻礙主線程的 UI 繪制等等。我們知道,為了讓屏幕的刷新幀率達到 60fps,我們需要確保 16ms 內完成單次刷新的操作。一旦我們在主線程裡面執行的任務過於繁重就可能導致接收到刷新信號的時候因為資源被佔用而無法完成這次刷新操作,這樣就會產生掉幀的現象,刷新幀率自然也就跟著下降了(一旦刷新幀率降到 20fps 左右,用戶就可以明顯感知到卡頓不流暢了)。
為了避免上面提到的掉幀問題,我們需要使用多線程的技術方案,把那些操作復雜的任務移動到其他線程當中執行,這樣就不容易阻塞主線程的操作,也就減小了出現掉幀的可能性。
那麼問題來了,為主線程減輕負的多線程方案有哪些呢?這些方案分別適合在什麼場景下使用?Android 系統為我們提供了若干組工具類來幫助解決這個問題。
AsyncTask: 為 UI 線程與工作線程之間進行快速的切換提供一種簡單便捷的機制。適用於當下立即需要啟動,但是非同步執行的生命周期短暫的使用場景。
HandlerThread: 為某些回調方法或者等待某些任務的執行設置一個專屬的線程,並提供線程任務的調度機制。
ThreadPool: 把任務分解成不同的單元,分發到各個不同的線程上,進行同時並發處理。
IntentService: 適合於執行由 UI 觸發的後台 Service 任務,並可以把後台任務執行的情況通過一定的機制反饋給 UI。
了解這些系統提供的多線程工具類分別適合在什麼場景下,可以幫助我們選擇合適的解決方案,避免出現不可預期的麻煩。雖然使用多線程可以提高程序的並發量,但是我們需要特別注意因為引入多線程而可能伴隨而來的內存問題。舉個例子,在 Activity 內部定義的一個 AsyncTask,它屬於一個內部類,該類本身和外面的 Activity 是有引用關系的,如果 Activity 要銷毀的時候,AsyncTask 還仍然在運行,這會導致 Activity 沒有辦法完全釋放,從而引發內存泄漏。所以說,多線程是提升程序性能的有效手段之一,但是使用多線程卻需要十分謹慎小心,如果不了解背後的執行機制以及使用的注意事項,很可能引起嚴重的問題。
『貳』 android多線程編程中,怎樣保證線程安全
有。 用 FutureTask 。
解釋: 主體工作你已經完成一半了。 目前的狀態是, 好比你分配完任務讓線程去處理。
線程還沒處理完,你還沒有得到結果你就先回去了。
怎麼等待某一個任務完成呢? 在 java 中你可以使用 FutureTask<V> 還封裝你的任務,表示這是一個將來某一個時間完成的任務,我們一般叫做非同步任務。
FutureTask<V> 主要是,在你調用它的`get` 方法時,哪顆它還沒有完成就在那裡等著,完成再返回給你結果。
『叄』 Android開發中多線程與UI更新
直接在UI線程中開啟子線程來更新TextView顯示的內容,運行程序我們會發現,如下錯誤:android.view.ViewRoot$: Only the original thread that created a view hierarchy can touch its views.翻譯過來就是:只有創建這個控制項的線程才能去更新該控制項的內容。
所有的UI線程要去負責View的創建並且維護它,例如更新冒個TextView的顯示,都必須在主線程中去做,我們不能直接在UI線程中去創建子線程,要利用消息機制:handler,如下就是handler的簡單工作原理圖:
既然android給我們提供了Handler機制來解決這樣的問題,請看如下代碼:
public class HandlerTestActivity extends Activity { private TextView tv; private static final int UPDATE = 0; private Handler handler = new Handler() { @Overridepublic void handleMessage(Message msg) { // TODO 接收消息並且去更新UI線程上的控制項內容if (msg.what == UPDATE) { // Bundle b = msg.getData();// tv.setText(b.getString("num")); tv.setText(String.valueOf(msg.obj)); } super.handleMessage(msg); } }; /** Called when the activity is first created. */@Overridepublic void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.main); tv = (TextView) findViewById(R.id.tv); new Thread() { @Overridepublic void run() { // TODO 子線程中通過handler發送消息給handler接收,由handler去更新TextView的值try { for (int i = 0; i < 100; i++) { Thread.sleep(500); Message msg = new Message(); msg.what = UPDATE; // Bundle b = new Bundle();// b.putString("num", "更新後的值:" + i);// msg.setData(b); msg.obj = "更新後的值:" + i; handler.sendMessage(msg); } } catch (InterruptedException e) { e.printStackTrace(); } } }.start(); }}
我們就通過Handler機制來處理了子線程去更新UI線程式控制制項問題,Andrid開發中要經常用到這種機制。
『肆』 android ,java多線程實現不了
newThread(){
publicvoidrun(){
for(inti=0;i<100;i++){
android.os.Messagemsg=newandroid.os.Message();
msg.what=0x0001;
msg.arg1=i;
hander.sendMessage
(msg);
try{
Thread.sleep(1000);
}catch(InterruptedExceptione){
e.printStackTrace();
}
}
}
}.start();
『伍』 Android開發中有哪些需要注意的多線程問題
方式1: 繼承Thread類,創建一個新的線程類。
private class thread extends Thread{
private Context act;
public thread(Context con){
act = con;
}
@Override
public void run() {
super.run();
//想要放到後台線程做的事情都寫在這里。
}
『陸』 Android 多線程與Java多線程比較 有哪些區別
在一個程序中,這些獨立運行的程序片斷叫作「線程」(Thread),利用它編程的概念就叫作「多線程處理」。多線程處理一個常見的例子就是用戶界面。利用線程,用戶可按下一個按鈕,然後程序會立即作出響應,而不是讓用戶等待程序完成了當前任務以後才開始響應。簡單地說,就是說可以有多個任務同時進行。
單線程在程序執行時,所走的程序路徑按照連續順序排下來,前面的必須處理好,後面的才會執行。因此,針對前面舉的例子,必須等待程序完成了當前任務以後才能開始相應。
使用多線程訪問公共的資源時,容易引發線程安全性問題,因此針對這種需要使用線程同步機制來保護公共的資源。
單線程較多線程來說,就不會出現上訴問題,系統穩定、擴展性極強、軟體豐富。多用於點對點的服務。
『柒』 Android開發中如何使用多線程
handler其實就是消息處理機制。首先在主線程也就是UI創建一個Handler對象,復寫其中的handMessage( Message msg)方法。該方法里的msg就是子線程發來的消息,表示子線程處理完了,以這個msg來通知主線程。讓主線程來作UI的繪制工作。
那麼子線程工作完了就要發消息了,比如:
run(){
data = getDataFromInternet();//耗時工作
Message msg = handler.obtainMessage(0, data);//通過handler得到消息,該消息的標識為0,消息內容是data
handler.sendMessage(msg);//發送
}
然後handler在主線程就負責接收:
public Handler handler = new Handler(){//處理UI繪制
@SuppressWarnings("unchecked")
@Override
public void handleMessage(Message msg) {
switch (msg.what) {
case 0:
data = (List<Map<String, Object>>) msg.obj;
if(data == null){
Toast.makeText(AllMovieActivity.this, "網路連接失敗,獲取不到影片信息", 1).show();
}else {
adapter = new HotMoviedapter(AllMovieActivity.this, data, R.layout.allmovielist_item,
new String[] { "picurl", "chname", "director", "leadrole",
"fshowtime", "country" }, new int[] { R.id.picurl,
R.id.chname, R.id.director, R.id.leadrole,
R.id.fshowtime, R.id.country },mListView);
TextView v = new TextView(AllMovieActivity.this);
v.setHeight(80);
v.setSelectAllOnFocus(false);
mListView.addFooterView(v);
mListView.setAdapter(adapter);
}
break;
default:
break;
}
}
};
『捌』 簡述android多線程機制
Handler對象與其調用者在同一線程中,如果在Handler中設置了延時操作,則調用線程也會堵塞。每個Handler對象都會綁定一個Looper對象,每個Looper對象對應一個消息隊列(MessageQueue)。如果在創建Handler時不指定與其綁定的Looper對象,系統默認會將當前線程的Looper綁定到該Handler上。在主線程中,可以直接使用newHandler()創建Handler對象,其將自動與主線程的Looper對象綁定;在非主線程中直接這樣創建Handler則會報錯,因為Android系統默認情況下非主線程中沒有開啟Looper,而Handler對象必須綁定Looper對象。這種情況下,需先在該線程中手動開啟Looper(Looper.prepare()-->Looper.loop()),然後將其綁定到Handler對象上;或者通過Looper.getMainLooper(),獲得主線程的Looper,將其綁定到此Handler對象上。Handler發送的消息都會加入到Looper的MessageQueue中。一說Handler包含兩個隊列:線程隊列和消息隊列;使用Handler.post()可以將線程對象加入到線程隊列中;使用Handler.sendMessage()可以將消息對象加入到消息隊列中。通過源碼分析證實,Handler只有一個消息隊列,即MessageQueue。通過post()傳進去的線程對象將會被封裝成消息對象後傳入MessageQueue。使用post()將線程對象放到消息隊列中後,當Looper輪詢到該線程執行時,實際上並不會單獨開啟一個新線程,而仍然在當前Looper綁定的線程中執行,Handler只是調用了該線程對象的run()而已。如,在子線程中定義了更新UI的指令,若直接開啟將該線程執行,則會報錯;而通過post()將其加入到主線程的Looper中並執行,就可以實現UI的更新。使用sendMessage()將消息對象加入到消息隊列後,當Looper輪詢到該消息時,就會調用Handler的handleMessage()來對其進行處理。再以更新UI為例,使用這種方法的話,就先將主線程的Looper綁定在Handler對象上,重載handleMessage()來處理UI更新,然後向其發送消息就可以了。
『玖』 java開發或者android開發中有沒有關於多線程的jar包
java.util.Random等
http://download.csdn.net/download/superww058/524951網站可以自己下載。
『拾』 android客戶端進行多線程編程的基本流程是怎樣的
話分兩頭:
第一:從RecentApp界面被劃掉後,系統做了什麼:
系統將這個應用的UI線程殺死,並將此應用當前所分配的內存空間回收。
第二:為什麼系統將UI線程殺死,將內存回收後,程序還能繼續工作?比如音樂還在繼續響起:
這是因為有一類應用,為了當用戶將此應用的界面調到後台後,仍然是可以工作,這些應用都會在後台開一個Service,你可以理解為一個區別於UI線程的另一個線程,它可以獨立於UI線程之外,當UI線程被掛起或者銷毀時,它可以接替UI線程的工作,讓程序員繼續work。所以,為什麼有時候程序被從Recent列表中刪除後,程序沒有停止,這里的停止,實質上是程序的某一功能沒有停止,比如音樂,而此時的程序UI界面以及其它無關的內存已經被告系統回收了。
第三:如何讓自己的應用不出現在Recent列表裡: