cafelier のSRM参加記録です。コンテスト中に考えてたことを執拗に全部書き残すとどうなるだろうかという試み本番中にこういうコードが書きたかったなあ、という後で書いた反省コードを書き残す試み
スパムが来たのでしばらくコメント欄をはてなユーザ限定にしています、すみません、
SRM | |
SRM494 の成績・ソース (要ログイン) : AC/AC/- : 花を摘んで花びら千切りながら「期待値、線形性、期待値、線形性、…」と占いを始めなければいけないレベル
class AlternatingLane { public: double expectedBeauty(vector <int> low, vector <int> high) { double eSum = 0.0; for(int i=1; i<low.size(); ++i) { // ランダムに // h ∈ [low[i-1], high[i-1]] // g ∈ [low[i], high[i] ] // を取ってきたときの、|h-g| の期待値… double e = 0; for(int h=low[i-1]; h<=high[i-1]; ++h) if( h <= low[i] ) e += sequenceSum(low[i]-h, high[i]-h); else if( high[i] <= h ) e += sequenceSum(h-high[i], h-low[i]); else e += sequenceSum(0, h-low[i]) + sequenceSum(0, high[i]-h); eSum += e / (high[i]-low[i]+1) / (high[i-1]-low[i-1]+1); } return eSum; // …の和、が答え } LL sequenceSum(LL a, LL b) // a+(a+1)+...+b { return (a+b) * (b-a+1) / 2; } };
class Painting { public: int largestBrush(vector <string> picture) { const int Y = picture.size(); const int X = picture[0].size(); int best = 1; for(int S=2; S<=min(Y,X); ++S) { vector<string> duty = picture; for(int y=0; y+S<=Y; ++y) for(int x=0; x+S<=X; ++x) if( all<'B'>(picture, y, x, y+S, x+S) ) // SxS の範囲が全部黒なら fill<'W'>(duty, y, x, y+S, x+S); // ここは塗れる if( all<'W'>(duty, 0, 0, Y, X) ) best = max(best, S); // 全部塗れてたらベストスコア更新 } return best; } template<char color> bool all(const vector<string>& p, int ys, int xs, int ye, int xe) { int cnt = 0; for(int y=ys; y<ye; ++y) for(int x=xs; x<xe; ++x) cnt += (p[y][x]==color); return cnt == (ye-ys)*(xe-xs); } template<char color> void fill(vector<string>& p, int ys, int xs, int ye, int xe) { for(int y=ys; y<ye; ++y) for(int x=xs; x<xe; ++x) p[y][x] = color; } };
WWBBWW WBBBBW BBWWBB BBWWBB WBBBBW WWBBWW
presented by cafelier/k.inaba under
cafelier2011/01/24 12:3750^4 は余裕で行けるとして50^5オーダのループはどのくらいまで通るのか問題。今回のだと
Σ_{S=1~N} (N-S)^2 S^2
= Σ_{S=1~N} ((N-S)S)^2
≦ Σ_{S=1~N} ((N/2)^2)^2(周の長さが同じなら長方形では正方形が一番デカい理論)
= N^5 / 16
≒ 2000万
くらいで評価すればいいのかな。Σ(N-k)k は N(N/2)^2 弱。