通常同步意味著一個任務的某個處理過程會對多個線程在用串行化處理,而異步則意味著某個處理過程可以允許多個線程同時處理。異步通常代表著更好的性能,因為它很大程度上依賴于緩沖,是典型的使用空間換時間的做法,例如在計算機當中,高速緩存作為cpu和磁盤io之間的緩沖地帶協調cpu高速計算能力和磁盤的低速讀寫能力。
十余年的大埔網站建設經驗,針對設計、前端、開發、售后、文案、推廣等六對一服務,響應快,48小時及時工作處理。營銷型網站建設的優勢是能夠根據用戶設備顯示端的尺寸不同,自動調整大埔建站的顯示方式,使網站能夠適用不同顯示終端,在瀏覽器中調整網站的寬度,無論在任何一種瀏覽器上瀏覽網站,都能展現優雅布局與設計,從而大程度地提升瀏覽體驗。成都創新互聯從事“大埔網站設計”,“大埔網站推廣”以來,每個客戶項目都認真落實執行。
(1):重新啟動一個java程序就啟動了一個進程
可以用操作系統命令行啟動 Runtime.getRuntime().exec("java -classpath . XXX");
(2):可不可以在接收消息的模塊中的addtolist函數中添加一個專門的處理函數,函數執行時先向list中添加消息,然后探測當前有沒有處理線程,如果沒有,則啟動線程。
(3):想省點工作,可以用BlockingQueue來代替list,這樣線程等待和喚醒不用寫代碼實現了,如果非要用list,那么就做好同步
list的小例子:
Java codeclass MessageConsumer extends Thead { ? ?private ListYourMessageType list; ? ?private boolean running = true; ? ?public MessageConsumer(ListYourMessageType list) {this.list = list;} ? ?public void run() { ? ? ? ?while (running) { ? ? ? ? ? ?YourMessageType msg = null; ? ? ? ? ? ? try { ? ? ? ? ? ? ? ?synchronized(list) { ? ? ? ? ? ? ? ? ? ?while (list.size() == 0) { ? ? ? ? ? ? ? ? ? ? ? ?list.wait(); ? ? ? ? ? ? ? ? ? ?} ? ? ? ? ? ? ? ? ? ?msg = list.remove(0); ? ? ? ? ? ? ? ? ? ?list.notiryAll(); ? ? ? ? ? ? ? ?} ? ? ? ? ? ?} catch (Exception e) { ? ? ? ? ? ? ? ?e.printStackTrace(); ? ? ? ? ? ?} ? ? ? ? ? ?if (msg == null) continue; ? ? ? ? ? ?//System.out.println(msg); //print message ? ? ? ?} ? ?}}//調用sampleclass ShareModule { ? ?ListYourMessageType list = new ArrayListYourMessageType(); ? ?...}public class Main { ? ?public static void main(String[] args) { ? ? ? ?ShareMudule sm; //so on ? ? ? ?... ? ? ? ?Thread t = new MessageConsumer(sm.list); ? ? ? ?t.start(); ? ? ? ?... ? ?}}
1. 使用wait和notify方法
這個方法其實是利用了鎖機制,直接貼代碼:
public class Demo1 extends BaseDemo{ private final Object lock = new Object(); @Override public void callback(long response) { System.out.println("得到結果"); System.out.println(response); System.out.println("調用結束"); synchronized (lock) { lock.notifyAll(); } } public static void main(String[] args) { Demo1 demo1 = new Demo1(); demo1.call(); synchronized (demo1.lock){ try { demo1.lock.wait(); } catch (InterruptedException e) { e.printStackTrace(); } } System.out.println("主線程內容"); } }
可以看到在發起調用后,主線程利用wait進行阻塞,等待回調中調用notify或者notifyAll方法來進行喚醒。注意,和大家認知的一樣,這里wait和notify都是需要先獲得對象的鎖的。在主線程中最后我們打印了一個內容,這也是用來驗證實驗結果的,如果沒有wait和notify,主線程內容會緊隨調用內容立刻打印;而像我們上面的代碼,主線程內容會一直等待回調函數調用結束才會進行打印。
沒有使用同步操作的情況下,打印結果:發起調用 調用返回 主線程內容 得到結果 1 調用結束
而使用了同步操作后:
發起調用 調用返回 得到結果 9 調用結束 主線程內容2. 使用條件鎖
和方法一的原理類似:
public class Demo2 extends BaseDemo { private final Lock lock = new ReentrantLock(); private final Condition con = lock.newCondition(); @Override public void callback(long response) { System.out.println("得到結果"); System.out.println(response); System.out.println("調用結束"); lock.lock(); try { con.signal(); }finally { lock.unlock(); } } public static void main(String[] args) { Demo2 demo2 = new Demo2(); demo2.call(); demo2.lock.lock(); try { demo2.con.await(); } catch (InterruptedException e) { e.printStackTrace(); }finally { demo2.lock.unlock(); } System.out.println("主線程內容"); } }
基本上和方法一沒什么區別,只是這里使用了條件鎖,兩者的鎖機制有所不同。
在整個思路上要調整一下
1、會有很多線程給一個隊列上添加任務
2、有一個或者多個線程逐個執行隊列的任務
考慮一下幾點:
1、沒有任務時,隊列執行線程處于等待狀態
2、添加任務時,激活隊列執行線程,全部run起來,首先搶到任務的執行,其他全部wait
給個小例子吧
package?org;
import?java.util.LinkedList;
import?java.util.List;
public?class?Queues?{
public?static?ListTask?queue?=?new?LinkedListTask();
/**
?*?假如?參數o?為任務
?*?@param?o
?*/
public?static?void?add?(Task?t){
synchronized?(Queues.queue)?{
Queues.queue.add(t);?//添加任務
Queues.queue.notifyAll();//激活該隊列對應的執行線程,全部Run起來
}
}
static?class?Task{
public?void?test(){
System.out.println("我被執行了");
}
}
}
package?org;
import?java.util.List;
public?class?Exec?implements?Runnable{
@Override
public?void?run()?{
while(true){
synchronized?(Queues.queue)?{
while(Queues.queue.isEmpty()){?//
try?{
Queues.queue.wait();?//隊列為空時,使線程處于等待狀態
}?catch?(InterruptedException?e)?{
e.printStackTrace();
}
System.out.println("wait...");
}
Queues.Task?t=?Queues.queue.remove(0);?//得到第一個
t.test();?//執行該任務
System.out.println("end");
}
}
}
public?static?void?main(String[]?args)?{
Exec?e?=?new?Exec();
for?(int?i?=?0;?i??2;?i++)?{
new?Thread(e).start();?//開始執行時,隊列為空,處于等待狀態
}
//上面開啟兩個線程執行隊列中的任務,那就是先到先得了
//添加一個任務測試
Queues.Task?t?=new?Queues.Task();
Queues.add(t);?//執行該方法,激活所有對應隊列,那兩個線程就會開始執行啦
}
}
上面的就是很簡單的例子了
網頁標題:異步java代碼,java異步執行代碼
本文地址:http://vcdvsql.cn/article28/hsdsjp.html
成都網站建設公司_創新互聯,為您提供App設計、域名注冊、服務器托管、軟件開發、搜索引擎優化、營銷型網站建設
聲明:本網站發布的內容(圖片、視頻和文字)以用戶投稿、用戶轉載內容為主,如果涉及侵權請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網站立場,如需處理請聯系客服。電話:028-86922220;郵箱:631063699@qq.com。內容未經允許不得轉載,或轉載時需注明來源: 創新互聯