Rubyスクリプトを主に実行しているサーバーがあります。Ruby(2.7)にはGILがあるため、シングルスレッドです。
私のコンピューター(サーバー)にはIntel i3デュアルコアプロセッサーが搭載されていますが、ハイパースレッディングにより4つのコアが表示されます。 Rubyは、高負荷で25%のCPUしか使用しません。ハイパースレッディングを無効にすると、シングルスレッドで実行されるプログラミング言語にメリットがあるかどうかを確認しました。
また、私のサーバーは非常に最小限のデスクトップ環境を実行しており、CPUを2%以上使用していません。そのため、Rubyで利用できるリソースのほとんどを作りたかったのです。ハイパースレッディングを無効にすることでパフォーマンスが向上するかどうかを確認するためにベンチマークを行いました。
簡単なRubyスクリプトを作成して、whileループを実行し、ループカウンターの値を別の変数で追加します。このプログラムは、CPUコアの100%を使用する必要があります。
#!/usr/bin/env Ruby
$-v = true
LOOPS = ENV['N'].to_i.then { |x| x < 1 ? 100_000_000 : x } + 1
i, j, t = 0, 0, Time.now
puts "Counting till #{LOOPS - 1} and adding values to V..."
while (i += 1) < LOOPS
if i % 10000 == 0
e = Time.now - t
r = LOOPS.*(e)./(i).-(e).round(2)
print "\e[2KN: #{i} | Done: #{i.*(100) / LOOPS}% | Elapsed: #{e.round(2)}s | Estimated Rem: #{r}s\r"
end
j += i
end
puts "\nV = #{j}\nTime: #{(Time.now).-(t).round(2)}s"
⮚ Ruby p.rb
Counting till 100000000 and adding values to V...
N: 100000000 | Done: 99% | Elapsed: 4.55s | Estimated Rem: 0.0s
V = 5000000050000000
Time: 4.55s
⮚ Ruby p.rb
Counting till 100000000 and adding values to V...
N: 100000000 | Done: 99% | Elapsed: 4.54s | Estimated Rem: 0.0s
V = 5000000050000000
Time: 4.54s
⮚ Ruby p.rb
Counting till 100000000 and adding values to V...
N: 100000000 | Done: 99% | Elapsed: 4.67s | Estimated Rem: 0.0s
V = 5000000050000000
Time: 4.67s
gnome-system-monitorは、テストの実行中にRuby)によって25%のCPU使用率を報告しました。
[# echo 0 | tee /sys/devices/system/cpu/cpu{2,3}/online
ハイパースレッドを無効にするために使用されます]
⮚ Ruby p.rb
Counting till 100000000 and adding values to V...
N: 100000000 | Done: 99% | Elapsed: 4.72s | Estimated Rem: 0.0s
V = 5000000050000000
Time: 4.72s
⮚ Ruby p.rb
Counting till 100000000 and adding values to V...
N: 100000000 | Done: 99% | Elapsed: 4.54s | Estimated Rem: 0.0s
V = 5000000050000000
Time: 4.54s
⮚ Ruby p.rb
Counting till 100000000 and adding values to V...
N: 100000000 | Done: 99% | Elapsed: 4.56s | Estimated Rem: 0.0s
V = 5000000050000000
Time: 4.56s
gnome-system-monitorテストの実行中に、Ruby)による50%のCPU使用率が報告されました。
私は自分のラップトップでテストを実行しましたが、これは私のコンピューターでかかった時間の約2倍かかります。しかし、結果は同じです。ハイパースレッディングを無効にしても、プロセスの改善には役立ちません。さらに悪いことに、私のラップトップはマルチタスクを実行すると少し遅くなります。
したがって、非ハイパースレッディングモードでは、Rubyはハイパースレッディングモードの2倍のCPUパワーを使用しましたが、同じタスクを完了するのに同じ時間を費やしたのはなぜですか?
あなたのRubyプログラムはnotを使用しました--- HTを無効にして実行すると、CPU時間の2倍を使用します。むしろ、2つの合計コアのうち1つのコアを最大化するため、gnome-system-monitor
は50%の使用率としてレポートします。 HTが原因で、システムが合計4つのコアを報告した場合、4つのうち1つのコアは25%になります。
HTを無効にすると、利用可能なリソースが少なくなるため、結果のばらつきが大きくなります。最近のIntel(またはAMD)コアは非常に幅が広いため、追加のスレッドは、多くの場合、合計パフォーマンスを10〜20%向上させるのに役立ちます。テストの実行中にバックグラウンドプロセスが自動的に実行された場合、HTのないシステムでは、分散が大きくなり、総スループットが低下する傾向があります。
ハイパースレッディングを無効にすると、シングルスレッドで実行されるプログラミング言語にメリットがあるかどうかを確認したかったのです。
コアの数を削減することで、シングルスレッドアプリでもパフォーマンスがどのように向上するかはわかりません。ハイパースレッディングを有効にすると、CPUは4つの仮想コアで実行されます。使用可能なすべてのCPUを使用するシングルスレッドアプリは、使用可能なCPUの25%を使用します。ハイパースレッディングを無効にすると、コアの数が2に減りました。これで、シングルスレッドアプリは使用可能なCPUの50%を使用できます。
Rubyは2倍のCPUを使用していません。ハイパースレッディングを無効にすると、CPUの半分が利用可能になります。 1/4の水が入った大きなカップがあり、1/2の水になる小さなカップに注いだ場合でも、同じ量の水があります。
私は自分のラップトップでテストを実行しましたが、これは私のコンピューターでかかった時間の約2倍かかります。しかし、結果は同じです。ハイパースレッディングを無効にしても、プロセスの改善には役立ちません。さらに悪いことに、私のラップトップはマルチタスクを実行すると少し遅くなります。
はい、CPUの電力の約半分を奪っています。 Rubyスレッドの実行も遅くなります。Rubyスレッドに加えて、同時に実行したいスレッドが3つあるとします。仮想コアを2に減らした場合、別のスレッドに一時停止させるために、Rubyスレッドが少なくとも少し一時停止される可能性が高くなります。