2012-08-29 29 views
1

嘿所以我拿起了這個用於執行ExecutorService的java文檔的例子。我想確認這段代碼的流程,Executors.newFixedThreadPool會創建一個線程池(我猜)。所以serversocket將等待連接,一旦它獲得一個連接,它就啓動一個線程,所以現在poolize減1。一旦線程完成執行,poolize會再次增加1,不會呢?線程會放棄它使用的資源嗎?在java中需要關於ExecutorService的建議

class NetworkService implements Runnable { 
private final ServerSocket serverSocket; 
private final ExecutorService pool; 

public NetworkService(int port, int poolSize) 
    throws IOException { 
serverSocket = new ServerSocket(port); 
pool = Executors.newFixedThreadPool(poolSize); 
} 

public void run() { // run the service 
try { 
    for (;;) { 
    pool.execute(new Handler(serverSocket.accept())); 
    } 
} catch (IOException ex) { 
    pool.shutdown(); 
    } 
} 
} 

class Handler implements Runnable { 
private final Socket socket; 
Handler(Socket socket) { this.socket = socket; } 
public void run() { 
    // read and service request on socket 
} 
} 

回答

0

所有線程要做的就是執行Runnable秒。
所以如果你需要做任何清潔後,你的任務做應該從你的Runnable做到這一點。該池只是一個Producer - Consumer模式實現,並負責管理線程的生命週期。
線程執行您在隊列中傳遞的任務,因此在您的情況下,線程間不會重複使用socket。它的範圍在Runnable

1

線程完成執行後,池大小會再次增加1,不會嗎?

是的。線程將採取並運行下一個Handler

線程會放棄它使用的資源嗎?

不立即,沒有。一旦Handlerrun()方法已完成然後Handler將超出範圍。但是,您必須等待垃圾收集器在Handler實例發佈之前運行。這將依次釋放Socket,然後它將成爲垃圾收集本身的候選對象。

如果你想要你的Socket更早釋放(我認爲是問題),那麼應該在run()方法的末尾完成。您可以在finally區塊中撥打socket.close()(也可能將socket設置爲null)。類似下面的建議:

class Handler implements Runnable { 
    ... 
    public void run() { 
     try { 
      // read and service request on socket 
     } finally { 
      // make sure we close the socket when the handler is finishing 
      socket.close(); 
     } 
    } 
} 
0

因爲它是一個fixedThreadPool,是的,池尺寸減小每次任務提交給池&增加一旦線程完成運行時所提交的可運行(或可調用) 。 將更多數量的可運行內容提交給固定線程池將阻塞,直到池中的任何線程完成運行其之前提交的任務。