タスクが 1 つだけの長時間実行される Spark ステージ
タスクが 1 つだけの長時間実行されるステージには並列性がありません。タスクがランしている間、1 つの CPU が処理を行い、残りのクラスターはアイドル状態になる可能性があります。Sparkはタスクをワーカー間で分散できないため、ワーカーを追加しても効果はありません。
最長のステージにタスクが 1 つしかない場合は、このページを使用します。ステージにタスクが多数ある場合は、スキューとspillを確認してください。Skew and spillを参照してください。
一般的な原因と修正
単一タスクのステージは、通常、次のいずれかが原因です。コードに当てはまるものを見つけて、修正を適用してください:
- 小規模なデータに対する高コストな UDF 。 入力が小さいと単一のパーティションに収まってしまうため、1 つのタスクが UDF 全体をランしてしまいます。可能であれば、ネイティブ関数を使用して UDF を書き換えてください。そうでない場合は、UDF を適用する前に DataFrame を
repartition()してください。低速な UDF を参照してください。 PARTITION BYのないウィンドウ関数。PARTITION BY句がない場合、ウィンドウはデータセット全体に及ぶため、1つのタスクですべての行が処理されます。ロジックで許可されている場合は、PARTITION BY句を追加します。- 分割不可能なファイルタイプ。 Sparkは、gzipファイルのようなファイルを複数のパートで読み取ることができないため、1つの大きなタスクで各ファイルを読み取ります。同じファイルを繰り返し読み取る場合は、そのファイルを一度Delta Lakeテーブルに取り込み、テーブルをクエリーしてください。
- JSONまたはCSVの読み取りにおける
multiLineオプション。 レコードが複数行にまたがる場合にのみ、multiLineを設定します。複数行JSONファイルの読み取りを参照してください。 - 大きなファイルでのスキーマ推論。 推論するのではなく、スキーマを指定してください。「スキーマの指定」を参照してください。
repartition(1)またはcoalesce(1)。 これらはすべてのデータを1つのパーティションに強制的に格納します。単一の出力ファイルが必要な場合を除き、これらを削除するか、より多くのパーティションを使用してください。