SuperCon2010予選通過報告とソース

去年優勝しましたZATORIKUは今年もSuperCon楽しませてもらいます。二連覇しますよ。

期末なのでこれ書いたら寝ます。

解法概要

  • mが奇数のとき0
  • そうでない場合、[ [0,1],[1,1] ]^nと[ [1,2],[1,3] ]^(m/2)のしかるべき位置の積
  • 行列累乗はバイナリ法を利用
  • O(l(log n+log m)) ただしl=600,000

最適化

  • 2x2の行列の累乗は2変数で表現できる、など、変数の削減→nについては内部ループ1回につき3回、mについては内部ループ1回につき4回の剰余演算(分岐なし)で可能
    • 変数削減したうえで、使う変数だけをまとめてブロックにすると、最適化がうまく効くのか、微妙に速くなったりした
  • nについては32乗、mについては16乗まではintの範囲に収まるのでprecalculate
    • すこし速くなったっぽい
  • ループのアンローリング
  • これで分岐がかなり減る

効果があったかはわからない

なお、以下の最適化は結局使わなかった

  • kの奇数因子についてMontgomery乗算の適用、kの2^n因子についてはビット演算。最後に結果を結合
    • 分岐が多くなるからだめだったのかも。または、Montgomeryのために必要なprecalculateに時間がかかったのかも

ところで

本選でCUDAなりOpenCLなりが使えたら面白そうだし話題性もあるしいいと思う。