//JOI2008 予選問題3 #include void check(int *p, int n, int col, int ntop, int ntail); int count = 0; int main() { int chara[10000], i, j, n, tmp, ans = 0; scanf("%d", &n); for(i = 0; i < n; i++) scanf("%d", &chara[i]); /*chara[0]からchara[n-1]まで、色を赤青黄に変え、 それぞれについていくつのキャラクタが消えるか調べる*/ for(i = 0; i < n; i++) { for(j = 1; j < 4; j++) { tmp = chara[i]; chara[i] = j; count = 0; check(chara, n, j, i, i+1); if(count > ans) ans = count; chara[i] = tmp; } } printf("%d\n", n - ans); return 0; } void check(int *p, int n, int col, int ntop, int ntail) { int i, top, tail, localcount = 0; i = ntop; while(i > -1){ //探索範囲がキャラクタ配列を超えないまで、負の方向に調べる if((*(p + i)) == col){ localcount++; } else break; i--; } top = i; i = ntail; while(i < n){ //探索範囲がキャラクタ配列を超えないまで、正の方向に調べる if((*(p + i)) == col){ localcount++; } else break; i++; } tail = i; if(localcount >= 4) { count += localcount; for(i = 1; i < 4; i++) check(p, n, i, top, tail); } } /* アルゴリズム 1.キャラクタを配列chara[i]に格納する。 2.i=0からi=nまでのそれぞれについて、chara[i]を赤青黄に変更した場合いくつ消えるか調べる check()関数 引数にキャラクタの配列、キャラクタの個数、chara[i]の色、探索点上、探索点下をとる。 例 chara[] ●●●●××××●●● (×は消えたキャラクタ、●の範囲を調べたい) この場合探索点上は3、探索点下は8になる 探索点から端に向かって調べていき、同じ色ならばlocalcountをインクリメントする。 localcountが4を超えれば、キャラクタの消滅が起きるのでキャラクタを消去する。 例 chara[] ●☆☆☆××××☆● (☆が消したいキャラクタ) この場合は、次に呼び出すcheck()の探索点上を0, 探索点下を9とすればよい。 キャラクタを消去したらその数だけcountを増やし、再びcheck()を呼び出す。 すべての色についてこれを行い、どの色の場合もlocalcountが4に達しない場合は呼び出しを終了する。 この時点でのcountの値が、chara[i]を色jに変えた場合に消えるキャラクタの個数になる。 */