解析ソルバー HiGHS C++ソースにおいて、高速化技術、C++の高速化・アルゴリズムの高速化、その他すべての高速化について、100個、あげて下さい。
引用 Google AI Studio
HiGHS(High-Performance Interior Point Solver / Simplex solver)のような高性能な数理最適化ソルバーのC++ソースコードにおける高速化技術を、アルゴリズム、実装(C++)、データ構造、ハードウェア最適化の観点から100個挙げます。
これらはHiGHSの設計思想や、一般的な高性能計算(HPC)の知見に基づいています。
I. アルゴリズム・数理最適化の高速化 (30個)
Dual Simplex法の採用: 多くのLP問題でPrimalより高速な傾向がある。
Steepest Edge Pricing: 収束を早めるための高品質なピボット選択。
Devex Pricing: Steepest edgeの近似による計算コスト削減。
Hyper-sparsity(超疎性)の活用: ベクトルのほとんどがゼロであることを利用した計算スキップ。
Presolve(前処理)の徹底: 変数固定、冗長な制約の削除による問題サイズの縮小。
Sparsity-preserving Factorization: フィルイン(非ゼロ要素の増加)を抑えるLU分解。
Markowitz Ordering: LU分解時のピボット選択によるスパース性の維持。
Periodic Refactorization: 蓄積した更新(Eta行列)をクリアし、LU分解を再計算して精度と速度を回復。
Forrest-Tomlin Update: 基底行列の更新を効率的に行う。
Harris' Two-pass Ratio Test: 数値的安定性を保ちつつ大きなステップサイズを確保。
Bound Flipping: 非基底変数の境界移動を一度の反復で複数行う。
Crossover: 内点法解から基底解(Simplex)へ高速に移行するアルゴリズム。
Interior Point Method (IPM) - Mehrotra's Predictor-Corrector: 反復回数を大幅に減らす。
AMD (Approximate Minimum Degree) Ordering: 行列の並び替えによる内点法の高速化。
Nested Dissection: 大規模行列の並列分解のための順序付け。
KKT系の正則化: 数値的不安定を回避し、反復の停滞を防ぐ。
Sparsification: 前処理で疎行列をさらに疎にする技術。
Dualization: 制約式数より変数が多い場合に双対問題を解く。
Scaling (Equilibration): 行列の条件数を改善し、収束を早める。
Crash Procedures: 最初の基底を賢く選び、反復回数を減らす。
Aggregate Constraints: 複数の制約を1つにまとめてサイズ削減。
Implied Bound Strengthening: 制約の組み合わせから変数の上下限を絞り込む。
Probing: 変数を0/1に仮定して矛盾を探り、ドメインを削る。
Heuristic Pricing: 厳密なPricingを避け、計算の軽い候補から選ぶ。
Dynamic Pricing Strategy: 状況に応じてPricingアルゴリズムを切り替える。
Numerical Tolerance Logic: 許容誤差を動的に調整し、無駄な反復を避ける。
Hot Start: 以前の解を基に、微修正された問題を高速に解く。
Infeasibility Analysis: 実行不能な場合に素早く判定を下す。
Long-step Rule (IPM): 内点法で境界付近まで一気に進む。
Branch-and-Bound Efficiency: MIP(混合整数計画)におけるノード探索の優先順位付け。
II. C++ 実装・メモリ管理の高速化 (25個)
Cache Localityの最適化: 行列をCSC(Compressed Sparse Column)形式で保持し、列スキャンを高速化。
Custom Allocators: std::vector 等の動的確保によるオーバーヘッドを避けるためのプールメモリ。
Vector Reserve: 再確保(Reallocation)を防ぐための事前の reserve()。
Avoid Virtual Functions: タイトなループ内でのポリモーフィズム(仮想関数呼び出し)を排除。
Inlining: inline キーワードやヘッダー実装による関数呼び出しコストの削減。
Constexpr: コンパイル時定数計算の活用。
Move Semantics: std::move による巨大行列データのコピー回避。
Alignment (std::align): CPUキャッシュラインに合わせたデータの配置。
Loop Unrolling: ループ展開によるブランチ予測ミスとオーバーヘッドの削減。
SIMD (AVX2/AVX-512) の活用: ベクトル演算(ドット積等)の並列化。
Structure of Arrays (SoA) vs AoS: 演算パターンに合わせたデータレイアウトの選択。
Pass by Reference/Pointer: 巨大オブジェクトのコピー渡し禁止。
Zero-initializationの最小化: 必要な領域だけ初期化。
Template Metaprogramming: 特定の行列サイズや型に特化したコードの生成。
Explicit Specifiers: 意図しない暗黙の型変換(と一時オブジェクト生成)の防止。
Fast I/O: std::endl を避け \n を使う、または fread/fwrite を活用。
Prefetching: __builtin_prefetch 等による次データの先行読み込み。
Avoid Exception in Hot Path: 実行速度が重要な箇所での例外スローを避ける。
Static Polymorphism (CRTP): 実行時ではなくコンパイル時にクラスを切り替える。
Efficient Bitsets: フラグ管理に std::vector<bool> ではなく、ビット演算を活用。
Small Vector Optimization: 要素が少ない場合に動的確保を避けるスタック利用。
Non-blocking Logging: ログ出力が計算スレッドを止めない工夫。
Pimpl Patternの制限: 実行速度優先箇所ではカプセル化よりインライン化を取る。
Local Variable Reuse: ループ内での一時変数の再利用。
Floating Point Fast Math: ffast-math フラグの使用(数値的精度とトレードオフ)。
III. 並列化・マルチスレッド (15個)
OpenMPによるループ並列化: Pricingや行列更新の並列化。
Task-based Parallelism: 依存関係のあるタスク(LU分解等)の効率的な実行。
Lock-free Data Structures: スレッド間の競合を減らす。
NUMA Awareness: 各CPUソケットに近いメモリにデータを配置。
Parallel Presolve: 互いに独立した制約の並列処理。
Concurrent Simplex: 異なる設定(Dual/Primal等)で同時に解き、早く終わった方を採用。
Atomic Operations: mutex を避けた軽量な同期。
Thread Affinity: スレッドを特定のCPUコアに固定。
False Sharingの回避: キャッシュラインを意識した変数の配置(alignas)。
Parallel Matrix-Vector Multiplication (SpMV): 内点法の中核演算の高速化。
Load Balancing: スレッド間の仕事量の均一化(動的スケジューリング)。
Granularity Control: 並列化の粒度を調整し、オーバーヘッドを抑制。
Distributed Memory Support (MPI): 複数ノードでの超大規模問題対応。
Asynchronous Iteration: 同期ポイントを減らした反復計算(特定の条件下)。
Scalable Memory Allocator: jemalloc や tcmalloc の使用によるスレッド間競合緩和。
IV. 数値線形代数・行列計算 (15個)
Block LU Factorization: キャッシュ効率を上げるためのブロック化。
Sparse BLAS: 特化した疎行列演算ライブラリの利用。
Iterative Refinement: 低精度の解を高速に求め、その後修正して精度を出す。
Partial Pivoting: 安定性と速度のバランスをとったピボット選択。
Rank-1 Update (Sherman-Morrison): 基底更新の簡略化。
Cholesky Factorization (IPM用): 対称正定値行列に特化した高速分解。
Symbolic Factorization: 非ゼロパターンの事前計算による実行時の計算削減。
Numerical Thresholding: 極小の値をゼロと見なし、疎性を維持。
Reordering for Cache: 行列の要素をメモリ連続的に並び替え。
Kernel Fusion: 複数のベクトル演算を1つのループにまとめ、メモリトラフィック削減。
Identity Submatrix Recognition: 基底行列内の単位行列部分の計算省略。
Singular Value Handling: 特異行列に近い場合の高速な回避策。
Exploiting Network Flow Structure: 問題の一部にネットワーク構造がある場合の特化アルゴリズム。
Diagonal Preconditioning: 対角スケーリングによる収束加速。
Reduced KKT System: 変数を消去し、解くべき行列サイズを半分にする。
V. アーキテクチャ・ツール・その他 (15個)
Link Time Optimization (LTO): コンパイルを跨いだ最適化。
Profile Guided Optimization (PGO): 実際の実行データに基づく最適化。
CPU Branch Prediction Tuning: if文の発生頻度を考慮したコード配置。
Instruction Cache Optimization: ホットな関数をメモリ上に集約。
Reduced Precision (Float16/32): 精度が許す範囲での低精度演算による高速化。
Native Compilation (-march=native): 実行CPUに特化した命令セットの使用。
Binary Layout Optimization: __builtin_expect (likely/unlikely) の活用。
Memory Mapped Files: 大規模問題の高速なロード。
Automated Tuning: ハイパーパラメータ(Pricing戦略等)の自動調整。
Minimal Dependencies: 外部ライブラリ呼び出しのオーバーヘッド削減。
Hardware Performance Counter Analysis: ボトルネック(キャッシュミス等)の特定。
Valgrind/Cachegrind による解析: メモリ効率の徹底的な改善。
Continuous Benchmarking: 性能退行の即時検知。
Vectorization Friendly Data Structures: ポインタの配列を避け、連続メモリを使用。
Loop Interchange: ネストされたループの順序を入れ替えてキャッシュヒット率向上。
これらの技術を組み合わせることで、HiGHSのようなソルバーは、ナイーブな実装よりも数万倍以上の速度を実現しています。特に**「超疎性(Hyper-sparsity)の活用」と「キャッシュ効率を意識した実装」**は、現代のCPUアーキテクチャにおいて最も重要な要素です