FifoPriorityThreadPoolExecutor.java revision b5419dc08eb0a0f82821d774435720e5a31bc936
1package com.bumptech.glide.load.engine.executor; 2 3import java.util.concurrent.FutureTask; 4import java.util.concurrent.PriorityBlockingQueue; 5import java.util.concurrent.RunnableFuture; 6import java.util.concurrent.ThreadFactory; 7import java.util.concurrent.ThreadPoolExecutor; 8import java.util.concurrent.TimeUnit; 9import java.util.concurrent.atomic.AtomicInteger; 10 11/** 12 * A FIFO priority {@link ThreadPoolExecutor} that prioritizes submitted {@link Runnable}s by assuming they implement 13 * {@link Prioritized}. {@link Prioritized} runnables that return lower values for {@link Prioritized#getPriority()} 14 * will be executed before those that return higher values. Priorities only apply when multiple items are queued at the 15 * same time. Runnables with the same priority will be executed in FIFO order. 16 */ 17public class FifoPriorityThreadPoolExecutor extends ThreadPoolExecutor { 18 AtomicInteger ordering = new AtomicInteger(); 19 20 /** 21 * Constructor to build a fixed thread pool with the given pool size using 22 * {@link com.bumptech.glide.load.engine.executor.FifoPriorityThreadPoolExecutor.DefaultThreadFactory}. 23 * 24 * @param poolSize The number of threads. 25 */ 26 public FifoPriorityThreadPoolExecutor(int poolSize) { 27 this(poolSize, poolSize, 0, TimeUnit.MILLISECONDS, new DefaultThreadFactory()); 28 } 29 30 public FifoPriorityThreadPoolExecutor(int corePoolSize, int maximumPoolSize, long keepAlive, TimeUnit timeUnit, 31 ThreadFactory threadFactory) { 32 super(corePoolSize, maximumPoolSize, keepAlive, timeUnit, new PriorityBlockingQueue<Runnable>(), threadFactory); 33 } 34 35 @Override 36 protected <T> RunnableFuture<T> newTaskFor(Runnable runnable, T value) { 37 return new FifoPriorityLoadTask<T>(runnable, value, ordering.getAndIncrement()); 38 } 39 40 /** 41 * A {@link java.util.concurrent.ThreadFactory} that builds threads with priority 42 * {@link android.os.Process#THREAD_PRIORITY_BACKGROUND}. 43 */ 44 public static class DefaultThreadFactory implements ThreadFactory { 45 int threadNum = 0; 46 @Override 47 public Thread newThread(Runnable runnable) { 48 final Thread result = new Thread(runnable, "fifo-pool-thread-" + threadNum) { 49 @Override 50 public void run() { 51 android.os.Process.setThreadPriority(android.os.Process.THREAD_PRIORITY_BACKGROUND); 52 super.run(); 53 } 54 }; 55 threadNum++; 56 return result; 57 } 58 } 59 60 private static class FifoPriorityLoadTask<T> extends FutureTask<T> implements Comparable<FifoPriorityLoadTask> { 61 private final int priority; 62 private final int order; 63 64 public FifoPriorityLoadTask(Runnable runnable, T result, int order) { 65 super(runnable, result); 66 if (!(runnable instanceof Prioritized)) { 67 throw new IllegalArgumentException("FifoPriorityThreadPoolExecutor must be given Runnables that " 68 + "implement Prioritized"); 69 } 70 priority = ((Prioritized) runnable).getPriority(); 71 this.order = order; 72 } 73 74 @Override 75 public int compareTo(FifoPriorityLoadTask loadTask) { 76 int result = priority - loadTask.priority; 77 if (result == 0 && loadTask != this) { 78 result = order - loadTask.order; 79 } 80 return result; 81 } 82 } 83} 84