Re: [問題] 使用thread更慢的問題

看板C_and_CPP作者 (Caesar)時間9年前 (2016/03/30 17:23), 9年前編輯推噓3(3010)
留言13則, 2人參與, 最新討論串2/3 (看更多)
原本要回你信,後來想說直接放版上好了,以便讓其他人看(也讓別人糾正自己的錯誤) 如果你仔細讀 http://en.cppreference.com/w/cpp/thread/async 你就會發現如果是用launch::async, "async executes the function f on a new thread of execution (with all thread-l ocals initialized) as if spawned by std::thread" 也就是說他的執行會 直接construct thread一樣 問題來了,這個像真的就會如同construct thread一樣嗎? 首先,需要先知道,每個CPU有最大能提供的threads數量(簡稱CPU threads) 而每個作業系統也有最大能提供的threads數量(簡稱OS threads) 如果在程式construct過多thread(如同你的arrayCount),有可能會導致system_error,這情況發生在 1. 你把所有OS threads都用完了 2. 你的OS有限制process能使用的threads數量 假設system_error的情況都沒有,那你還會面對別的問題,context switch 一旦你的construct threads的數量大於CPU threads,就會需要context switch context switch會增加程式執行時間,因為 1. 它減少每個threads能使用的時間 2. context switch本身就需要時間,而它成本不低 講了那麼多,那async可以做什麼? 原因是async本身可以幫你解決掉context switch所產生的問題 (如果你是用launch::async|launch::deferred,那還可以解決system_error的問題) 雖然說async的行為 直接construct thread,但它內部如果只用固定N個threads輪流 執行 那他就不需要context switch,所以async可以更快 std::thread因為有提供native_handle,它可以做更多async做不到的事情(例如設定pri ority (而且thread每次construct都需要system call,async可以用threadpool解決這問題) 如果你不需要用native_handle,那你就應該使用async 或是你可以自己寫threadpool來使用(或是用intel TBB,感謝LiloHuang補充) 但我目前沒看到有好的threadpool可以滿足以下四點 1. exception safety 2. work stealing 3. pure C++ 4. thread-safe(這看起來好像很基本,但github搜索threadpool第一頁的 第3(nbsdx)與第5(tghosgor)的threadpool都沒做到) 即便是我自己寫的threadpool,目前1與2都沒做到(1快做到了) 即使都做到了,也還有dynamic resize threadpool可以研究 另外,關於你說的 : 我想std::thread應該也是在new thread中執行, 但難道它是以同步的方式嗎? 所有thread應該都算是asynchronous(非同步) 但是asynchronous本來是用來形容IO的 你拿asynchronous形容thread的執行方式,好像怪怪的 -- ※ 發信站: 批踢踢實業坊(ptt.cc), 來自: 1.171.69.132 ※ 文章網址: https://www.ptt.cc/bbs/C_and_CPP/M.1459329789.A.F5D.html

03/30 18:08, , 1F
Intel TBB library 本身就能滿足你那四點
03/30 18:08, 1F

03/30 18:10, , 2F
MSVC 的 std::async 在 launch::async 是用 PPL 實作
03/30 18:10, 2F

03/30 18:12, , 3F
無論是 PPL 或者 TBB 都是 threadpool,後者彈性非常大
03/30 18:12, 3F

03/30 18:17, , 4F
TBB 強大於 parallelism functions (i.e. flow graph)
03/30 18:17, 4F

03/30 18:18, , 5F
用以實作各種複雜的 structured parallel patterns
03/30 18:18, 5F

04/04 02:40, , 6F
MSVC使用PPL實作←這可以從哪邊查到?
04/04 02:40, 6F

04/04 02:53, , 7F
所以比起thread, async提供一套管理(優化)平行處理的方
04/04 02:53, 7F

04/04 02:54, , 8F
式, 而thread並沒有這套機制. 可以這樣理解嗎?
04/04 02:54, 8F
是的,不過標準並沒有規定async要做threadpool(因此最差的情況,就只不過跟construc t thread一樣) ※ 編輯: Caesar08 (114.136.62.215), 04/04/2016 10:14:48

04/08 20:19, , 9F
MSVC使用PPL這件事情你可以自己單步追蹤,會發現是使用
04/08 20:19, 9F

04/08 20:19, , 10F
::Concurrency::create_task() 來建立一個 async task
04/08 20:19, 10F

04/09 18:34, , 11F
除了動手trace, msdn或文件上是否有提到?
04/09 18:34, 11F

04/10 10:50, , 12F
我不記得 MSDN 有提到,因為這算是內部實作的細節。
04/10 10:50, 12F

04/10 10:52, , 13F
如果怕實作在未來改變,就直接使用 PPL 或者 TBB。
04/10 10:52, 13F
※ 編輯: Caesar08 (140.114.233.71), 07/13/2016 22:56:57
文章代碼(AID): #1M-vhzzT (C_and_CPP)
文章代碼(AID): #1M-vhzzT (C_and_CPP)