// OB会夏合宿2011 Day4 E : 落書きの魔女 #include #include #include #include using namespace std; int encode(vector vi){ int n = vi.size(); vector idx(8,0); int res = 0, cnt = 1; for(int i=0;i> H >> W){ for(int i=0;i> s[i]; map< int, int > mp[2]; mp[0][0] = 0; int cur = 0, next = 1; for(int i=0;i::iterator it=mp[cur].begin();it!=mp[cur].end();it++){ int val = it->first; bool space = (s[i][j]!='#'), wall = (s[i][j]!='.'); vector state(W); for(int k=W-1;k>=0;val/=8) state[k--] = val%8; // 色を塗ってないマスに接してたら色を塗らなくてはいけない if((i!=0&&state[0]==0)||(j!=0&&state[W-1]==0)) space = false; // 上の場所と同じ連結成分の場所が他になければ色を塗らなくてはいけない if(W!=1){ bool flg = state[0]!=0; for(int k=1;ksecond > 0) wall = false; } // 接する2つの場所が同じ連結成分なら色は塗れない if(i!=0&&j!=0&&state[0]!=0&&state[0]==state[W-1]) wall = false; // 色を塗らないとき if(space){ int t = state[0]; state[0] = 0; int tmp = encode(state); mp[next][tmp] = max(mp[next][tmp], it->second); state[0] = t; } // 色を塗るとき if(wall){ // 上のマスと左のマスが同じ連結成分になる if(j!=0&&state[W-1]!=0&&i!=0&&state[0]!=0){ for(int k=1;ksecond+1); } } mp[cur].clear(); swap(cur, next); } } int res = -1; for(map::iterator it=mp[cur].begin();it!=mp[cur].end();it++){ bool ok = true; for(int i=0;ifirst>>(3*i))%8) > 1) ok = false; if(ok) res = max(res, it->second); } cout << res << endl; } }