PyTorch Profilerでボトルネックを特定:`torch.profiler.ProfilerActivity`でパフォーマンスを向上させる
torch.profiler.ProfilerActivity
は、PyTorch Profiler で使用される列挙体であり、プロファイリング対象となるアクティビティグループを指定するために使用されます。各アクティビティグループは、異なるハードウェアまたはソフトウェアコンポーネントでの計算を表現します。
利用可能なアクティビティグループ
NETWORK
: ネットワーク通信に関するイベントをプロファイリングします。DISK
: ディスク入出力に関するイベントをプロファイリングします。KEYBOARD
: キーボード入力に関するイベントをプロファイリングします。CUDA
: GPU 上で行われる計算をプロファイリングします。CPU
: CPU 上で行われる計算をプロファイリングします。
import torch.profiler as profiler
with profiler.profile(activities=[profiler.ProfilerActivity.CPU, profiler.ProfilerActivity.CUDA]):
# モデルを実行
model(input_data)
# プロファイリング結果を分析
profiler.schedule
関数を使用して、プロファイリングを動的に制御することもできます。- デフォルトでは、すべての
ProfilerActivity
がプロファイリング対象となります。 - 複数の
ProfilerActivity
を組み合わせて指定することができます。
- パフォーマンスボトルネックの特定方法
- プロファイリング結果の分析方法
- 特定のユースケースにおける
ProfilerActivity
の使い分け
CPU と GPU のアクティビティのみをプロファイリング
import torch
import torch.profiler as profiler
model = torch.nn.Sequential(
torch.nn.Linear(10, 64),
torch.nn.ReLU(),
torch.nn.Linear(64, 10)
)
input_data = torch.randn(128, 10)
with profiler.profile(activities=[profiler.ProfilerActivity.CPU, profiler.ProfilerActivity.CUDA]):
output = model(input_data)
# プロファイリング結果を分析
print(profiler.get_profile())
このコードでは、profiler.profile
コンテキストマネージャーを使用して、CPU と GPU 上でのみアクティビティをプロファイリングするように指定しています。
キーボード入力とネットワーク通信のアクティビティもプロファイリング
import torch
import torch.profiler as profiler
model = torch.nn.Sequential(
torch.nn.Linear(10, 64),
torch.nn.ReLU(),
torch.nn.Linear(64, 10)
)
input_data = torch.randn(128, 10)
with profiler.profile(activities=[
profiler.ProfilerActivity.CPU,
profiler.ProfilerActivity.CUDA,
profiler.ProfilerActivity.KEYBOARD,
profiler.ProfilerActivity.NETWORK
]):
output = model(input_data)
# プロファイリング結果を分析
print(profiler.get_profile())
このコードでは、activities
リストに KEYBOARD
と NETWORK
を追加することで、キーボード入力とネットワーク通信に関するアクティビティもプロファイリング対象に含めています。
import torch
import torch.profiler as profiler
model = torch.nn.Sequential(
torch.nn.Linear(10, 64),
torch.nn.ReLU(),
torch.nn.Linear(64, 10)
)
input_data = torch.randn(128, 10)
start_iter = 10
end_iter = 20
with profiler.profile(activities=[profiler.ProfilerActivity.CPU, profiler.ProfilerActivity.CUDA]) as prof:
for i in range(30):
if start_iter <= i <= end_iter:
prof.enable()
output = model(input_data)
if start_iter <= i <= end_iter:
prof.disable()
# プロファイリング結果を分析
print(profiler.get_profile())
このコードでは、profiler.profile
コンテキストマネージャーの enable()
と disable()
メソッドを使用して、特定のイテレーション (10 番目から 20 番目) のみプロファイリングするようにしています。
これらの例は、torch.profiler.ProfilerActivity
を使用して、PyTorch モデルのパフォーマンスを分析するための出発点となるものです。具体的なニーズに合わせて、これらのコードを自由に拡張して、より詳細なプロファイリングを行うことができます。
- より複雑なプロファイリングシナリオについては、PyTorch Profiler ドキュメントを参照してください。
- 上記のコード例はあくまでも基本的な例であり、実際のユースケースに合わせて調整する必要があります。
autograd.profiler モジュール
torch.profiler.ProfilerActivity
が導入される以前は、autograd.profiler
モジュールが主にプロファイリングに使用されていました。このモジュールは、ProfilerActivity
と同等の機能を提供しており、現在でも単純なプロファイリングシナリオで使用することができます。
例:autograd.profiler
を使用した CPU と GPU のアクティビティのみをプロファイリング
import torch
import autograd.profiler as profiler
model = torch.nn.Sequential(
torch.nn.Linear(10, 64),
torch.nn.ReLU(),
torch.nn.Linear(64, 10)
)
input_data = torch.randn(128, 10)
with profiler.profile():
output = model(input_data)
# プロファイリング結果を分析
print(profiler.print_profile())
trace モジュール
trace
モジュールは、PyTorch モデルの計算グラフをトレースし、各ノードにかかる時間とメモリ使用量を分析することができます。ProfilerActivity
と異なり、trace
はハードウェアに依存しないプロファイリング情報を提供します。
例:trace
モジュールを使用してモデル全体のプロファイリング
import torch
import torch.jit.trace as trace
model = torch.nn.Sequential(
torch.nn.Linear(10, 64),
torch.nn.ReLU(),
torch.nn.Linear(64, 10)
)
input_data = torch.randn(128, 10)
trace_model = trace.trace(model, input_data)
trace_model.eval()
# プロファイリング結果を分析
print(trace_model.graph_summary())
サードパーティ製ライブラリ
torch.profiler.ProfilerActivity
を使用する際の注意点
- サードパーティ製のライブラリは、より高度な機能を提供する場合がありますが、商用ライセンスが必要となる場合があります。
- 複雑なプロファイリングシナリオでは、
autograd.profiler
やtrace
モジュールのほうが適切な場合もあります。 torch.profiler.ProfilerActivity
は、比較的新しい機能であり、まだ完全ではない可能性があります。
torch.profiler.ProfilerActivity
は、PyTorch Profiler でプロファイリング対象となるアクティビティグループを指定するための便利なツールですが、状況に応じて他の方法も検討する必要があります。