在java中实现线程的方式:javascript
main方法其实也是一个线程。
在java中,每次程序运行至少启动2个线程。一个是main线程,一个是垃圾收集线程。java
yield()方法并发
Thread.yield()方法做用是:暂停当前正在执行的线程对象,并执行其余线程。
yield()应该作的是让当前运行线程回到可运行状态,以容许具备相同优先级的其余线程得到运行机会。所以,使用yield()的目的是让相同优先级的线程之间能适当的轮转执行。可是,实际中没法保证yield()达到让步目的,由于让步的线程还有可能被线程调度程序再次选中。异步
结论:yield()从未致使线程转到等待/睡眠/阻塞状态。在大多数状况下,yield()将致使线程从运行状态转到可运行状态,但有可能没有效果。async
join()方法
保证当前线程中止执行,直到该线程所加入的线程完成为止,当前线程方可继续执行。然而,若是它加入的线程没有存活,则当前线程不须要中止。ide
执行流程:
构造方法中实例化WorkerRunnable和FutureTask对象。
WorkerRunnable将Params参数封装,并将本身封装在FutureTask中,一旦FutureTask执行run方法时,会去调用WorkRunnable的call方法并返回Result值。call方法中就执行了AsyncTask的doInBackground方法。并调用postResult方法将结果发送出去。oop
mWorker = new WorkerRunnable<Params, Result>() {
public Result call() throws Exception {
mTaskInvoked.set(true);
Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
//noinspection unchecked
Result result = doInBackground(mParams);
Binder.flushPendingCommands();
return postResult(result);
}
};
private Result postResult(Result result) {
@SuppressWarnings("unchecked")
Message message = getHandler().obtainMessage(MESSAGE_POST_RESULT,
new AsyncTaskResult<Result>(this, result));
message.sendToTarget();
return result;
}复制代码
那么FutureTask是何时执行的?
FutureTask充当了Runnable的做用,交给SerialExecutor的execute方法执行。FutureTask是一个并发类,能够中途取消的用于异步计算的类。post
SerialExecutor的execute方法首先把FutureTask插入到mTasks任务队列中,若是没有活动的任务,则执行下一个。当一个任务执行完成,会继续调用scheduleNext方法执行下一个,直到全部任务都被执行。性能
THREAD_POOL_EXECUTOR.execute(mActive);才是真正执行任务的方法。使用的是ThreadPoolExecutor线程池。ui
private static class SerialExecutor implements Executor {
final ArrayDeque<Runnable> mTasks = new ArrayDeque<Runnable>();
Runnable mActive;
public synchronized void execute(final Runnable r) {
//将FutureTask插入到mTasks任务队列中
mTasks.offer(new Runnable() {
public void run() {
try {
// 执行FutureTask的run方法,进而执行call方法
r.run();
} finally {
// 串行执行下一个任务
scheduleNext();
}
}
});
//没有正在活动的任务,执行下一个AsyncTask。
if (mActive == null) {
scheduleNext();
}
}
protected synchronized void scheduleNext() {
if ((mActive = mTasks.poll()) != null) {
THREAD_POOL_EXECUTOR.execute(mActive);
}
}
}复制代码
注意:
继承了Thread类,本质仍是线程。可是能够直接使用Handler的Thread。在run方法中经过Looper.prepare建立消息队列,并开启消息循环。使得能够再次线程中建立Handler。
同时,它还解决了一个Looper与Handler的同步问题。能够保证根据当前线程的Looper建立Handler时,Looper对象的获取不为空。
参考《深刻理解Android 卷I》159页
/** * This method returns the Looper associated with this thread. If this thread not been started * or for any reason is isAlive() returns false, this method will return null. If this thread * has been started, this method will block until the looper has been initialized. * @return The looper. */
public Looper getLooper() {
if (!isAlive()) {
return null;
}
// If the thread has been started, wait until the looper has been created.
synchronized (this) {
while (isAlive() && mLooper == null) {
try {
wait();
} catch (InterruptedException e) {
}
}
}
return mLooper;
}复制代码
因为loop开启了无限循环,所以能够经过quit或者quitSafely方法终止线程执行。
典型应用场景就是在IntentService中。
@Override
public void run() {
mTid = Process.myTid();
Looper.prepare();
synchronized (this) {
mLooper = Looper.myLooper();
notifyAll();
}
Process.setThreadPriority(mPriority);
onLooperPrepared();
Looper.loop();
mTid = -1;
}复制代码
一个能够处理异步请求的Service.服务开启后,工做线程会依次处理每一个Intent,任务执行完毕后会自动关闭。
相对于线程而言,IntentService更适合执行一些高优先级的后台任务。
@Override
public void onCreate() {
// TODO: It would be nice to have an option to hold a partial wakelock
// during processing, and to have a static startService(Context, Intent)
// method that would launch the service & hand off a wakelock.
super.onCreate();
HandlerThread thread = new HandlerThread("IntentService[" + mName + "]");
thread.start();
mServiceLooper = thread.getLooper();
mServiceHandler = new ServiceHandler(mServiceLooper);
}复制代码
public ThreadPoolExecutor(int corePoolSize,
int maximumPoolSize,
long keepAliveTime,
TimeUnit unit,
BlockingQueue<Runnable> workQueue,
ThreadFactory threadFactory,
RejectedExecutionHandler handler) { }复制代码
变量
规则