上一篇 <<<并發(fā)隊(duì)列
下一篇 >>>Fork/Join框架
Callable與Future模式:Callable用來(lái)執(zhí)行任務(wù),F(xiàn)uture用來(lái)獲得結(jié)果鹉胖。
底層的原理主要采用wait和notify
Future提供的功能
(1)能夠中斷執(zhí)行中的任務(wù)
(2)判斷任務(wù)是否執(zhí)行完成
(3)獲取任務(wù)執(zhí)行完成后的結(jié)果馋袜。
Future常用方法
V get() :獲取異步執(zhí)行的結(jié)果司浪,如果沒(méi)有結(jié)果可用荧关,此方法會(huì)阻塞直到異步計(jì)算完成省骂。
V get(Long timeout , TimeUnit unit) :獲取異步執(zhí)行結(jié)果举户,如果沒(méi)有結(jié)果可用尤仍,此方法會(huì)阻塞,但是會(huì)有時(shí)間限制蔼紧,如果阻塞時(shí)間超過(guò)設(shè)定的timeout時(shí)間婆硬,該方法將拋出異常。
boolean isDone() :如果任務(wù)執(zhí)行結(jié)束奸例,無(wú)論是正常結(jié)束或是中途取消還是發(fā)生異常彬犯,都返回true。
boolean isCanceller() :如果任務(wù)完成前被取消,則返回true躏嚎。
boolean cancel(boolean mayInterruptRunning) :如果任務(wù)還沒(méi)開(kāi)始,執(zhí)行cancel(...)方法將返回false菩貌;如果任務(wù)已經(jīng)啟動(dòng)卢佣,執(zhí)行cancel(true)方法將以中斷執(zhí)行此任務(wù)線程的方式來(lái)試圖停止任務(wù),如果停止成功箭阶,返回true虚茶;當(dāng)任務(wù)已經(jīng)啟動(dòng),執(zhí)行cancel(false)方法將不會(huì)對(duì)正在執(zhí)行的任務(wù)線程產(chǎn)生影響(讓線程正常執(zhí)行到完成)仇参,此時(shí)返回false嘹叫;當(dāng)任務(wù)已經(jīng)完成,執(zhí)行cancel(...)方法將返回false诈乒。mayInterruptRunning參數(shù)表示是否中斷執(zhí)行中的線程罩扇。
Callable的優(yōu)勢(shì)
a、有返回
b怕磨、主線程不用等待
核心代碼
ExecutorService executor = Executors.newCachedThreadPool();
Future<Integer> future = executor.submit(new AddNumberTask());
System.out.println(Thread.currentThread().getName() + "線程執(zhí)行其他任務(wù)");
Integer integer = future.get();
System.out.println(integer);
// 關(guān)閉線程池
if (executor != null) {
executor.shutdown();
}
手寫(xiě)Callable與Future模式核心思路
public void run() {
result = myCallable.call();
// 喚醒阻塞線程
LockSupport.unpark(curThread);
// 也可以使用下列方式喚醒
/*synchronized (lock) {
lock.notify();
}*/
}
/**
* 結(jié)果返回
* @return
*/
public V get() {
// 獲取結(jié)果喂饥,則直接返回
if (result != null) {
return result;
}
// 獲得當(dāng)前線程
curThread = Thread.currentThread();
// 未獲得結(jié)果,則先阻塞肠鲫,等run方法執(zhí)行完成調(diào)用unpark后员帮,自動(dòng)繼續(xù)執(zhí)行
LockSupport.park(curThread);
// 也可以使用下列方式阻塞
/*synchronized (lock) {
try {
lock.wait();
} catch (Exception e) {
}
}*/
return result;
}
MyTask<String> myTask = new MyTask<>(new MyCallableImpl());
new Thread(myTask).start();
String s = myTask.get();
System.out.println(s);
相關(guān)文章鏈接:
<<<多線程基礎(chǔ)
<<<線程安全與解決方案
<<<鎖的深入化
<<<鎖的優(yōu)化
<<<Java內(nèi)存模型(JMM)
<<<Volatile解決JMM的可見(jiàn)性問(wèn)題
<<<Volatile的偽共享和重排序
<<<CAS無(wú)鎖模式及ABA問(wèn)題
<<<Synchronized鎖
<<<Lock鎖
<<<AQS同步器
<<<Condition
<<<CountDownLatch同步計(jì)數(shù)器
<<<Semaphore信號(hào)量
<<<CyclicBarrier屏障
<<<線程池
<<<并發(fā)隊(duì)列
<<<Fork/Join框架
<<<Threadlocal
<<<Disruptor框架
<<<如何優(yōu)化多線程總結(jié)