自分でランダムケースをつくってバグとりをする方法(Chokudaiさんのツイートから)
Chokudaiさんのツイートから
この一連のツイート、まぁ流れちゃうので誰かQiitaとかにパクって書いてくれてもいいのよ。https://t.co/5HHCbR90KD
— chokudai(高橋 直大)🌸🍆 (@chokudai) August 16, 2020
回答部分と入力部分の分離
まずこんな感じで、回答部分と入力部分を分離して関数家します。こうしてあげるだけで今後の処理がちょっと簡単になる感じ。入力および出力がsolverの中から消えるようにするのがポイント。
比較解法のsolver2をつくって比較テストをする
次に、TLEとなる愚直解solver2を作ります。入力を除外しているので、この時点で愚直解と比較したいろんなテストが出来ます。
この時点で怪しい入力をいくつか試して、答えが合わない解が見つけられたら勝ち。
Submission #15986762 - AtCoder Beginner Contest 175
ランダムテストをためす
もし見つけられなかった場合は、一回入力を捨ててランダムテストをたくさん試しましょう。
愚直解はKが大きいと動かないので、Kを小さくしてランダムで動かしてみる感じ。答えが一致したらスルー、一致しなかったらそれを出力、って感じにすると良い。
こうするとダメな時の解が見つけられて良い感じ!
Submission #15987037 - AtCoder Beginner Contest 175
OKしかでなかった場合は?
これで例えばX,Dも小さい範囲で試すと実は動いちゃうんだけど、OKしか出なかった場合は、
・そもそも愚直解の考え方or実装が間違っている
・大きいケースでだけ動かない(=9割以上オーバーフロー)
のどっちかなので、どちらかを疑えばOK。考えることが減って嬉しくなる感じ。
ランダムつくるところだけ
自分でランダムケースつくってためすときに、自分で大きな数次々試すのは大変だなと思ってたので、テストケースを乱数で生成して試すのはなるほどでした。
乱数の作り方を知らなかったのでその部分だけ再掲します。
#include <bits/stdc++.h> using namespace std; int main(){ random_device seed_gen; mt19937_64 engine(seed_gen()); for(int i=0;i<100;i++){ long long x= engine() % (long long)1e15 +1; cout<<x<<endl; } return 0; }