題:
我可以使用Raspberry Pi CPU的所有4個內核嗎?
NaN
2017-11-22 05:28:07 UTC
view on stackexchange narkive permalink

我想知道是否有一種簡單的方法可以“打開”所有100%的CPU,以便我可以更快地運行進程(例如python計算)。

1)可以嗎?

2)是否有一種簡單的方法可以恢復到正常狀態?

3)是否可以使用較少的CPU

是否正在考慮進行命令行交互,例如:

pi @ raspberry:〜$ sudo turnOnFourCores python run.py

最簡潔的答案是不
長答案是“如果就這麼簡單,那將是默認值”
您的評論都具有誤導性,可能暗示Pi具有4個內核,但僅使用過1個。更好的答案是所有四個內核* ARE *均已啟用,但是Python(就此而言,以及其他任何程序)僅會除非它們是多線程的,否則使用多個內核。由於全局解釋器鎖定,即使使用多線程,Python仍然可以有效地停留在單核上,但這超出了此問題的範圍。
需要澄清的是,我認為OP對多核CPU的工作方式存在誤解,您的回答只會加劇他們的誤解。
使Python程序更快的最簡單方法是用編譯語言進行重寫(或至少使時間緊迫的任務使用c模塊)。
相關文章:[單個線程如何在多個內核上運行?](https://softwareengineering.stackexchange.com/a/350024/165079):我的回答涉及現代CPU如何查找和利用細粒度的一些細節。指令級並行性。 (但是請注意,RPi3使用有序的Cortex-A53 CPU內核。它們每個都是2寬超標量(ILP允許,每個時鐘2條指令),但是無法對指令進行重新排序以查找並行度並隱藏延遲。
HTTPS://嗚嗚嗚.software coven.com/parallel-computing-in-embedded-Mobile-devices/
在某些情況下,運行多個進程可以滿足您的需求。例如,您可以運行`gzip a&gzip b`而不是運行`gzip a b`。您可以修改run.py使其獨立工作嗎?請注意,該問題的解決方案與Pi無關,任何具有多個CPU的unixy計算機的行為都相似。
我同意@Sohcahtoa82。我知道多核CPU的工作原理,但對Pi平台並不十分熟悉,當我到達此頁面並開始從上到下閱讀時,我的第一印像是存在一些特定的限制(例如功耗或功耗)。東西)實際上阻止了Pi的CPU使用其所有內核。因為那是第一批評論員給我的印象。
使用[CPU頻率縮放](https://wiki.linuxaudio.org/wiki/raspberrypi),[調整](http://www.raspberry-pi-geek.com/Archive/2013/01/Timely-tips- for-speeding-up-up-up-您的Raspberry-Pi)或[超頻](https://haydenjames.io/raspberry-pi-3-overclock/)。使RPi進入類似於RTOS的操作模式,可能會大大有利於長時間/複雜的執行。另外,如果不採取預防措施,由於過熱或電流過大,RPi最大值將經常關閉。
十二 答案:
lights0123
2017-11-22 05:59:18 UTC
view on stackexchange narkive permalink

默認情況下,任何計算機都將盡可能使用其所有內核。但是,只有在應用程序為多線程時,它才能實現此目的。如果不是(即不使用 threading 模塊的Python腳本),則它最多只能使用一個內核。這相當於四核CPU上CPU的25%。如果要修改腳本以使用多個內核,可以將計算分為多個部分,並對其進行多線程處理,如 Python文檔所示。

更新:

正如 Anon回答,如果不使用Python的GIL(全局解釋器鎖),它將無法正常工作。這允許任務同時(看似)運行,但不允許代碼跨多個內核運行。如果您使用的是用C語言編寫的模塊(例如numpy),則它們可以允許您使用多個內核來解決該限制。此外,如果不是這樣,Python將提供 multiprocessing,它允許您在多個內核上運行任何任務。

該更新-是正確的-解釋了為什麼答案的第一部分相對於Python是錯誤的。您只能通過編寫模塊C或某種編譯語言來克服Python的這種局限性,此時,您將不再真正編寫Python。如果性能至關重要,那麼使用編譯語言是正確的答案。 (從資源使用的角度來看,多處理*不是*相同的。)
-1
更令人困惑的是,Python _is_已編譯;對於CPython,它將編譯為在CPython VM中運行的CPython字節碼。對於Jython,它被編譯為Java字節碼,並在JVM中運行。最後,IronPython編譯為針對.NET運行時的CIL。因此,““使用一種已編譯的語言” _以取得性能並不是很有意義;)
*任何計算機都將盡可能嘗試使用其所有內核。*並非如此,*告訴*時,它只會使用其所有內核(或執行其他任何操作)。對於經驗豐富的人來說,這種區別似乎顯而易見,甚至是光顧的,但聽起來OP需意識到它不會自動發生。
goldilocks
2017-11-22 05:58:41 UTC
view on stackexchange narkive permalink

我想知道是否有一種簡單的方法可以“打開”所有100%的CPU,以便我可以更快地運行進程(例如python計算)。

不是我認為您是在暗示。這不是pi特有的問題,這是一個邏輯約束。

所有單獨的計算機當前沒有足夠的能力來確定某個進程作為單個線程運行可以並行運行。請注意,在他們可能具有此功能的時候,將不需要計算機程序員,因為可以執行此操作的計算機系統也可以編寫自己的代碼 1。 sup>。

考慮以下簡單的數學表達式:

 (4 + 2)* 17 /(3 + 6) 

可以並行計算,但在邏輯上受到限制。我會說沒有多於兩個線程是沒有意義的,即使那樣,它基本上只會是一個:

 #1 a)4 + 2 b)6 * 17 c)102 / 9#2 a)3 + 6  

線程#2通過計算3 + 6 = 9,由線程#1在步驟C中使用,節省了一步。但是,就並行性而言,這將是有益的。當線程#2 可以計算17/9時,#1執行6 * 17時,這樣做將毫無意義,因為您現在有兩個不同的路徑無法實現同一目標。即,#2可以繼續工作:

  b)17/9 c)1.888 * 6  

並最終得到與線程#1相同的結果(11.333),但是他們沒有在步驟A之外互相幫助,因此讓他們兩個追求這個目標是浪費時間。

(請注意,這個示例不是字面上的示例;它旨在演示邏輯原理。在用戶代碼中線程執行任務的規模要大得多,但是您無需在多線程編程中真正上課就可以掌握這裡的思想。)

利用多個處理器需要編寫相應的代碼。您不能簡單地說:“哦,使用所有4個內核,然後做得更快!”。那不會發生的。從邏輯上講,許多(或大多數)問題和任務涉及不能並行執行的步驟,它們必須順序執行。


1。但是請參見下面的Felix Dombek的評論;我不是AI方面的專家。值得一提的是,根據Peter Corde的評論,操作系統可以利用現代指令集和處理器以並行方式優化非常細粒度的事物,並且硬件管道也可以做到這一點,儘管不是跨內核的(單個內核正在進行的事情不止一件,在最終執行指令之前的不同時間對指令流進行操作)。我試圖在此處堅持用戶線程的主題,因為我認為這或多或少是您得到的。 sup>

我已經寫了很多並行的數字代碼,這對於細節有些誤導。您不會在這樣的單個算術運算級別上並行化。 (如果我們擴展到Raspberry Pi之外,無論如何,一些編譯器和處理器已經可以並行化其中的一些線程,甚至在線程結構之外。)您可以將整個任務並行化為更大的塊。
@Brick“您不會在這樣的單個算術運算級別上並行化。” ->當然不是,但是我會更明確地指出*這是一個類比,而不是一nuts不漏的多線程編程課程。
您作為示例使用的計算中的並行性是如此本地化,以至於它將在計算該程序的程序中創建[指令級並行性]亂序執行*可以*自己利用並行性。
RPi3使用2階有序超標量https://en.wikipedia.org/wiki/ARM_Cortex-A53,因此,通過精心安排指令,編譯器仍然可以通過將兩個“ add”指令彼此相鄰來利用ILP,因此它們都可以在同一時鐘週期內運行。但是,正如您指出的那樣,以下乘除法餘數將通過數據依賴關係進行序列化。
確定可並行化部分不一定需要強大的AI。從“一般”意義上講,它可能;但是很容易想到計算機可以使用某種啟發式方法,這種方法在許多實際情況下通常都有效。就像,計算機沒有證明費馬的最後定理,但是肯定有定理證明程序。請注意,用於編程語言的現代編譯器已經在優化步驟中進行了大量代碼重新排列,這涉及對可並行部分的推理。
@FelixDombek已完成;我也將其轉換為腳註,其中還包含Peter Corde的評論中的一些內容。 WRT計算機會自動進行並行化,我試圖強調(不要太過技術性或旁觀性),這不是目前在高級代碼中以嚴肅的廣泛方式進行的事情,也就是說,這是人類在代碼中實現的事情,並且對此有邏輯約束。
Anon
2017-11-22 06:56:54 UTC
view on stackexchange narkive permalink

不支持python。

其他人建議您研究線程化,這對大多數語言都是有效的答案,但他們沒有考慮到您使用的是python。

p>

Python GIL不允許您有效地利用多個內核。

GIL使使用所有4個內核“稍微困難”一些。它絕不會使它變得不可能,甚至沒有那麼大的挑戰性。
Peter Cordes
2017-11-22 14:40:40 UTC
view on stackexchange narkive permalink

使用多個內核需要將線程級並行性顯式地公開給OS,這通常需要程序員編寫多線程程序。 (或者在不同的輸入上多次運行單線程程序,例如使用 make -j4 進行編譯)

某些語言的編譯器支持自動並行化。例如,具有OpenMP的C或C ++可以將普通的 for()循環編譯到啟動多個線程的程序中。

  #pragma omp parallel forfor(int i = 0; i < 1000000; ++ i){A [i] = B [i] *常數+ C [i];}  

但是,在您編寫時,這必鬚髮生或編譯程序。 當前的硬件和操作系統無法使用多個內核來加速單線程程序。


相關:單線程如何運行在多個內核上?:答案是:不是。但是還有其他種類的並行性,例如指令級並行性,單個CPU內核發現並利用該並行性運行單個線程的速度比一次執行一條指令快。

我的回答關於這個問題的細節涉及現代CPU如何查找和利用細粒度的指令級並行性的一些細節。 (主要關注x86)。通過同時運行多個指令,這只是正常CPU工作方式的一部分,而無需特別啟用。 (不過,有一些性能計數器可以讓您查看CPU在執行程序時每個時鐘設法運行多少條指令,或者採取其他措施。)

請注意,RPi3使用有序 ARM Cortex-A53 CPU內核。每個內核都是2寬的超標量(ILP允許,每個時鐘2條指令),但是不能對指令重新排序以找到更多的指令級並行性並隱藏延遲。

儘管如此,CPU是流水線化的,所以正在運行的指令總數(從獲取和解碼一直到流水線末尾的寫回階段)非常重要。當數據依賴性不受限制時,CPU正在處理的每個管道階段可以有2條指令,每個時鐘的吞吐量為2條指令。 (這是2-wide的意思。)

它不能無序地執行指令,但是通過謹慎的指令排序(通常由編譯器執行),它仍然可以隱藏需要多個週期的指令的延遲。準備好輸出。 (例如,即使加載到緩存中或多次加載,加載也要花費多個週期,而下一個週期要準備好加法)。技巧是對asm指令進行排序,以便在生成結果的那一條與使用結果的那一條之間有多個獨立的指令。可以在內部重新排序,同時保留以程序順序運行的錯覺。對於編譯器來說,即使是很小的無序窗口也很難很好地完成指令的重新排序,因為緩存丟失是不可預測的,並且在編譯時很難分析跨函數調用的依賴鏈。沒有硬件寄存器重命名的情況下,寄存器的數量是有限的。


當您的代碼運行速度比您想要的慢時,所有這些都會帶來很小的舒適感。當然,Cortex-A53的引擎蓋下有很多很酷的東西,但 Cortex-A57的引擎蓋下還有很多很酷的東西(例如每個命令最多無序執行3條指令)時鐘),甚至在像Skylake這樣的大型x86 CPU中更是如此(更不用說時鐘速度差異了。)

https://en.wikipedia相比,Cortex-A53真是太棒了.org / wiki / Classic_RISC_pipeline就像您在計算機體系結構類中學習的原始MIPS一樣,但是按照現代標準,它是相當低端的。

“當前的硬件和操作系統無法使用多個內核來加速單線程程序。”並非完全正確。例如,在一個單線程Java程序中,Java可以在其他CPU內核上完成所有GC以及運行時分析/編譯。運行時分析很重要,因為它可以決定在運行代碼路徑的基礎上進行一些優化,而不會花費您的“單線程”任何東西,並且可以利用從分析中學到的知識極大地加快運行速度。一般來說,您的觀點是好的。
-1
沒錯,我只是指出,根據運行時的設計方式,即使是單線程的“編寫代碼”也可以利用額外的內核,而無需將其明確編碼為多線程應用程序。 Python也可以提供更強大的運行時,但是這毫無意義。無論如何,這都不是一個大的飛躍-我認為甚至Java都僅像額外的1/2內核一樣使用單線程應用程序。
“ *當前的硬件和操作系統無法使用多個內核來加快單線程程序的速度。*”,此後立即說明硬件如何並行執行指令。
@ThomasWeller是的,但是要挑剔的處理器流水線不使用多個內核;它包含在一個內核中,但是它允許在多個指令流上工作。也就是說,它*是*並行性的一種形式,但*不是*多核線程的一種形式。
我很好奇,為什麼這個答案有2票否決票。我相信它在技術上是準確的,但是也許這不是解釋線程級與指令級並行性的正確地方嗎?對於某些人來說,這是否太技術性或誤導性?
Jacobm001
2017-11-22 05:55:58 UTC
view on stackexchange narkive permalink

這根本不是CPU的工作方式。

按照目前的狀態,假設您的CPU不會由於溫度相關的問題而受到限制,那麼它完全能夠以100%的使用率運行在攝氏80度或以上。話雖這麼說,您(通常)不想看到CPU固定在100%。如果您的CPU利用率通常為100%,則處理器可能要處理的過多。這會造成結結,並給用戶帶來普遍不愉快的體驗。這輛車可能能夠以每小時100英里的速度行駛,但是您的車速表很有可能會在該速度下讀取一些東西。在城裡時,您可能永遠無法達到每小時25英里的速度。但是這並不能改變汽車可以以每小時100英里的速度行駛。您只是沒有足夠地用力推動加速器。

如果僅使RPi做更多的事情(在加速器上施加更多的推動力),您將看到CPU利用率上升。例如,在終端窗口中運行命令 yes 時,請注意CPU的使用情況(請記住, ctrl + c 會終止終端命令)。這將使您的CPU增加25%,因為它將使您的四個CPU內核之一最大化。

我認為這個答案會誤導您說您通常不希望CPU以100%的利用率運行。在許多數字密集型應用程序中,您絕對希望100%的利用率,因為您已經將一台或多台機器專用於計算。為了獲得真正的超級計算機時間,您通常必須*證明*您的代碼已被充分優化以執行此操作,否則它們將浪費您的資源。如果您擁有Pi群集,顯然您將無法獲得超級計算機的性能,但這可能會使最大化使用而不是更少變得更加關鍵!
我有點同意Brick的意思,在這裡似乎暗示著,如果處理器的使用率為25%,那是因為它是節省氣體或遵守速度限制;)或禮貌而不浪費資源。您可能需要使它更清楚一點,通常是因為無論什麼時候任務都在等待I / O。可以一直運行在一個核心上的事物將會。 (理想情況下)阻止此操作中斷用戶界面的是時間劃分-但實際上,堵塞一台小型單核計算機仍然很容易。
100%CPU使用率通常不會導致不良UX。即使大多數程序不受CPU限制,也受其他因素限制,即使1000%也足夠好。由於極端的CPU負載而變慢的唯一程序是一直在實際使用CPU的程序。
Stese
2017-11-22 14:28:07 UTC
view on stackexchange narkive permalink

其他答案確實提供了詳細的信息,但似乎並沒有專門解決您的問題。

  1. 是的,如果程序(和操作系統)被編程為考慮多個核。 (這裡的“線程”是編程中的術語)。
  2. 該計算機使用每個核心所需的內核數量,以完成任務。因此,無需更改任何內容。
  3. 您可以設置最大使用量限制,但在正常使用情況下無需如此。在這裡查看答案:- https://unix.stackexchange.com/questions/151883/limiting-processes-to-not-exceed-more-than-10-of-cpu-usage
  4. ol>

    NB:

    如果要提高pi的整體性能,則可能需要研究Overclocking。這樣可以使CPU以更快的速度運行。缺點是發熱量增加,處理器壽命降低以及功耗增加。

NikoNyrh
2017-11-22 22:13:34 UTC
view on stackexchange narkive permalink

如果可能的話,我將參數化腳本並在單獨的Python進程中執行它們。例如:

  cat parameters.txt | xargs -n1 -P4 python run.py  

另一種選擇是已經提到的多處理庫,該庫允許您分叉並加入python進程。但這還要求您具有要為其運行計算的參數列表(例如文件名)。

第一部分:是的,假設手頭的問題是[令人尷尬的並行](https://en.wikipedia.org/wiki/Embarrassingly_parallel)。
阿哈,是的,我只對多處理的處理池“ map”很熟悉,但顯然它也有許多相當複雜的共享內存結構。
silgon
2017-11-22 22:07:45 UTC
view on stackexchange narkive permalink

如果要測試RPI。您可以像在此處中那樣運行 stress ,然後您可以查看如何將CPU與 htop 一起使用。這很有用,因為您可以查看電源是否足夠,如果不夠,則RPI將嘗試使用過多的電流(安培),並且將關閉。

另一方面,如果您要使用python腳本,您應該看到 joblib ,當您要並行化進程時,該函數非常有用,因此您將使用所需的處理器數量。

sonofusion82
2017-11-23 07:53:41 UTC
view on stackexchange narkive permalink

我認為OP可能無法完全理解多核/多線程編程的概念以及如何充分利用100%的多核有多困難,除非可以輕鬆地將該算法製成令人尷尬的並行 >問題。

有關更多信息,您可以閱讀有關著名文章“免費午餐結束”的更多信息。 http://www.gotw.ca/publications/concurrency-ddj。 htm

paddyg
2017-11-24 00:43:19 UTC
view on stackexchange narkive permalink

儘管所有這些答案在不同方面都是正確的,但確實操作系統將自動使用不同的內核來分散負載。您可以使用簡單的python程序(temp.py這樣說)

  True:x = 1.0  

從RPi桌面打開一個終端,然後鍵入 $ top 將顯示處理器的工作。然後打開另一個終端並 python3 temp.py ,您將看到python3作業的處理器時間增加了100%。然後打開另一個終端並重複該過程,看看如何提高到400%。因此,在@Shadow註釋的一級上,它是如此簡單,並且它是默認設置。但是,正如其他人所解釋的那樣,設計可以使用並行處理的程序並非易事。

Orubel
2018-06-19 00:47:03 UTC
view on stackexchange narkive permalink

答案是肯定的!您只需編寫程序即可識別它們並使用它們。這樣做的程序可以使用內核。我用Java編寫了代碼,因此可以。

Python開發人員提供的上述答案對該答案的概念非常有限,因此可能會非常令人困惑,但是答案是“是”,只有“是”!

你能詳細說明一下嗎?
NomadMaker
2018-06-19 03:32:50 UTC
view on stackexchange narkive permalink

由於OP在他的問題中未指定python,所以我想建議另外兩種在Raspberry Pi上都能正常工作並且使用並發性非常簡單的現代語言。

我目前最喜歡的是Rust語言。我已經在Pi上編寫和編譯了程序。 Rust很不錯,因為它可以防止多種類型的指針和競爭條件錯誤,這使得編寫並發代碼既容易又安全。 Rust原本是一種系統編程語言,但是它幾乎可以執行C可以做的任何事情。 Go是由Google團隊創建的,是一種相當成熟的語言。在Go中創建協程很容易,他們稱之為“ Go例程”。

這兩種語言都可以在Raspberry Pi甚至Pi Zero上編譯代碼。但是,它們都可以從速度更快的計算機進行交叉編譯,這對於大型程序來說很不錯。



該問答將自動從英語翻譯而來。原始內容可在stackexchange上找到,我們感謝它分發的cc by-sa 3.0許可。
Loading...