當要使用大量的非同步任務,不想每次都創建子線程,可以使用 ExecutorService(線程池),令到減輕每個非同步任務的調用開銷和提高性能。
Android ExecutorService(線程池) |
- 每次 new Thread() 耗費性能
- 調用 new Thread() 創建的線程缺乏管理,被稱為野線程,而且可以無限制創建,之間相互競爭,會導致過多佔用系統資源導致系統癱瘓
- 不利於擴展,比如如定時執行、定期執行、線程中斷
ExecutorService 的優點:
- 重用存在的線程,減少物件創建、消亡的開銷,性能佳
- 可有效控制最大併發線程數,提高系統資源的使用率,同時避免過多資源競爭,避免堵塞,提供定時執行、定期執行、單線程、併發數控制等功能
通過 Executors 的靜態方法來創建,一般有三種:
- 單線程:Executors.newSingleThreadExecutor()
- 固定數量線程:Executors.newFixedThreadPool()
- 動態線程:Executors.newCachedThreadPool()
ThreadPoolExecutor 類的典型構造:
public ThreadPoolExecutor(int corePoolSize, int maximumPoolSize, long keepAliveTime, TimeUnit unit, BlockingQueue<Runnable> workQueue) { this(corePoolSize, maximumPoolSize, keepAliveTime, unit, workQueue, Executors.defaultThreadFactory(), defaultHandler); } |
ThreadPoolExecutor 的配置參數:
public ThreadPoolExecutor(int corePoolSize, int maximumPoolSize, long keepAliveTime, TimeUnit unit, BlockingQueue workQueue, ThreadFactory threadFactory, RejectedExecutionHandler handler) { this.corePoolSize = corePoolSize; this.maximumPoolSize = maximumPoolSize; this.workQueue = workQueue; this.keepAliveTime = unit.toNanos(keepAliveTime); this.threadFactory = threadFactory; this.handler = handler; } |
操作系統:Windows 7 64-bit 版本
開發環境:Android Studio 4.0.1 版本
原程式:C:\Development\Development_Android\Android_Project\DIY-Android-009-01D ExecutorService
程式:C:\Development\Development_Android\Android_Project\DIY-Android-009-01D ExecutorService
MainActivity.xml:
import androidx.appcompat.app.AppCompatActivity; import android.os.Bundle; import android.view.View; import android.widget.TextView; import java.util.concurrent.LinkedBlockingDeque; import java.util.concurrent.ThreadPoolExecutor; import java.util.concurrent.TimeUnit;
public class MainActivity extends AppCompatActivity {
// Gets the number of available cores (not always the same as the maximum number of cores) private static int NUMBER_OF_CORES = Runtime.getRuntime().availableProcessors(); // Sets the amount of time an idle thread waits before terminating private static final int KEEP_ALIVE_TIME = 1000; // Sets the Time Unit to Milliseconds private static final TimeUnit KEEP_ALIVE_TIME_UNIT = TimeUnit.MILLISECONDS; // Used to update UI with work progress private int count = 0;
@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); }
// This is the runnable task that we will run 100 times private Runnable runnable = new Runnable() { @Override public void run() { // Do some work that takes 100 milliseconds try { Thread.sleep(100); } catch (InterruptedException e) { e.printStackTrace(); }
// Update the UI with progress runOnUiThread(new Runnable() { @Override public void run() { count++; String msg = count < 100 ? "Thread Working " : "Finished ... "; updateStatus(msg + count); } }); } };
// Button click and performs work using a thread pool public void buttonClickThreadPool(View view) { count = 0; ThreadPoolExecutor mThreadPoolExecutor = new ThreadPoolExecutor( NUMBER_OF_CORES + 2, // Initial pool size NUMBER_OF_CORES + 2, // Max pool size KEEP_ALIVE_TIME, // Time idle thread waits before terminating KEEP_ALIVE_TIME_UNIT, // Sets the Time Unit for KEEP_ALIVE_TIME new LinkedBlockingDeque<Runnable>()); // Work Queue for (int i = 0; i < 100; i++) { mThreadPoolExecutor.execute(runnable); } }
private void updateStatus(String msg) { ((TextView) findViewById(R.id.text)).setText(msg); } } |
active_main.xml:
<?xml version="1.0" encoding="utf-8"?> <ScrollView xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="wrap_content" android:fillViewport="false"> <LinearLayout android:orientation="vertical" android:layout_width="match_parent" android:layout_height="match_parent">
<TextView android:id="@+id/text" android:layout_width="match_parent" android:layout_height="53dp" android:text="TextView" />
<Button android:id="@+id/poolButton" android:layout_width="match_parent" android:layout_height="wrap_content" android:onClick="buttonClickThreadPool" android:text="Thread Pool" /> </LinearLayout> </ScrollView> |
Android Studio ExecutorService(線程池)程式 |
沒有留言:
張貼留言