結果

問題 No.421 しろくろチョコレート
ユーザー rpy3cpprpy3cpp
提出日時 2016-09-09 23:34:21
言語 Python3
(3.12.2 + numpy 1.26.4 + scipy 1.12.0)
結果
AC  
実行時間 1,105 ms / 2,000 ms
コード長 3,220 bytes
コンパイル時間 94 ms
コンパイル使用メモリ 12,928 KB
実行使用メモリ 12,800 KB
最終ジャッジ日時 2024-09-23 07:06:53
合計ジャッジ時間 7,025 ms
ジャッジサーバーID
(参考情報)
judge1 / judge2
このコードへのチャレンジ
(要ログイン)

テストケース

テストケース表示
入力 結果 実行時間
実行使用メモリ
testcase_00 AC 32 ms
11,136 KB
testcase_01 AC 101 ms
11,648 KB
testcase_02 AC 43 ms
11,264 KB
testcase_03 AC 34 ms
11,008 KB
testcase_04 AC 37 ms
11,008 KB
testcase_05 AC 39 ms
11,008 KB
testcase_06 AC 34 ms
11,136 KB
testcase_07 AC 66 ms
11,392 KB
testcase_08 AC 42 ms
11,136 KB
testcase_09 AC 35 ms
11,008 KB
testcase_10 AC 35 ms
11,136 KB
testcase_11 AC 61 ms
11,520 KB
testcase_12 AC 33 ms
11,008 KB
testcase_13 AC 31 ms
11,008 KB
testcase_14 AC 31 ms
10,880 KB
testcase_15 AC 31 ms
11,008 KB
testcase_16 AC 134 ms
12,032 KB
testcase_17 AC 186 ms
12,160 KB
testcase_18 AC 215 ms
12,032 KB
testcase_19 AC 31 ms
11,008 KB
testcase_20 AC 102 ms
11,776 KB
testcase_21 AC 134 ms
11,776 KB
testcase_22 AC 61 ms
11,520 KB
testcase_23 AC 31 ms
11,136 KB
testcase_24 AC 31 ms
10,880 KB
testcase_25 AC 31 ms
11,136 KB
testcase_26 AC 31 ms
11,008 KB
testcase_27 AC 32 ms
11,008 KB
testcase_28 AC 47 ms
11,648 KB
testcase_29 AC 52 ms
11,776 KB
testcase_30 AC 58 ms
11,648 KB
testcase_31 AC 87 ms
12,800 KB
testcase_32 AC 57 ms
11,648 KB
testcase_33 AC 70 ms
11,776 KB
testcase_34 AC 34 ms
11,136 KB
testcase_35 AC 34 ms
11,008 KB
testcase_36 AC 74 ms
11,392 KB
testcase_37 AC 159 ms
12,160 KB
testcase_38 AC 213 ms
12,288 KB
testcase_39 AC 53 ms
11,392 KB
testcase_40 AC 81 ms
11,520 KB
testcase_41 AC 39 ms
11,136 KB
testcase_42 AC 37 ms
11,136 KB
testcase_43 AC 55 ms
11,392 KB
testcase_44 AC 113 ms
12,032 KB
testcase_45 AC 38 ms
11,008 KB
testcase_46 AC 43 ms
11,136 KB
testcase_47 AC 97 ms
11,648 KB
testcase_48 AC 1,105 ms
12,288 KB
testcase_49 AC 53 ms
11,264 KB
testcase_50 AC 41 ms
11,136 KB
testcase_51 AC 125 ms
12,032 KB
testcase_52 AC 65 ms
11,392 KB
testcase_53 AC 35 ms
11,136 KB
testcase_54 AC 44 ms
11,136 KB
testcase_55 AC 34 ms
11,008 KB
testcase_56 AC 35 ms
11,136 KB
testcase_57 AC 40 ms
11,008 KB
testcase_58 AC 97 ms
11,648 KB
testcase_59 AC 45 ms
11,264 KB
testcase_60 AC 276 ms
12,416 KB
testcase_61 AC 176 ms
12,544 KB
testcase_62 AC 31 ms
11,008 KB
testcase_63 AC 31 ms
11,008 KB
testcase_64 AC 31 ms
11,008 KB
権限があれば一括ダウンロードができます

ソースコード

diff #

def bp_match(Ss, Ts, Es):
    '''2部グラフのマッチング問題をとく。
    '''
    super_source = len(Ss) + len(Ts)
    super_target = super_source + 1
    Cs = [dict() for i in range(super_target + 1)]
    for si, ti in Es:
        Cs[si][ti] = 1
        Cs[ti][si] = 0
    for si in Ss:
        Cs[super_source][si] = 1
        Cs[si][super_source] = 0
    for ti in Ts:
        Cs[super_target][ti] = 0
        Cs[ti][super_target] = 1
    return dinic(Cs, super_target + 1, super_source, super_target)

def dinic(cf, nV, s, t):
    dist = get_distance(cf, s, t)
    while dist[t] > 0:
        df = dfs(dist, cf, s, t, float('inf'))
        while df:
            df = dfs(dist, cf, s, t, float('inf'))
        dist = get_distance(cf, s, t)
    return sum(cf[t].values())

def get_distance(cf, s, t):
    dist = [-1] * len(cf)
    dist[s] = 0
    frontiers = [s]
    while frontiers:
        new_frontiers = []
        for u in frontiers:
            for v, capacity in cf[u].items():
                if dist[v] == -1 and capacity > 0:
                    dist[v] = dist[u] + 1
                    new_frontiers.append(v)
        frontiers = new_frontiers
    return dist

def dfs(dist, cf, u, t, df):
    if u == t:
        return df
    for v, capacity in cf[u].items():
        if dist[v] > dist[u] and capacity > 0:
            new_df = dfs(dist, cf, v, t, min(df, capacity))
            if new_df > 0:
                cf[u][v] -= new_df
                cf[v][u] += new_df
                return new_df
    return 0


def read_data():
    N, M = map(int, input().split())
    Ws = []
    Bs = []
    Es = []
    for i in range(N):
        Si = input()
        for j, s in enumerate(Si):
            if s == '.':
                continue
            elif s == 'w':
                Ws.append(i * M + j)
            elif s == 'b':
                Bs.append(i * M + j)
    Bset = set(Bs)
    for w in Ws:
        i, j = divmod(w, M)
        if i > 0 and w - M in Bset:
            Es.append((w, w - M))
        if w + M in Bset:
            Es.append((w, w + M))
        if j > 0 and w - 1 in Bset:
            Es.append((w, w - 1))
        if j < M - 1 and w + 1 in Bset:
            Es.append((w, w + 1))
    return N, M, Ws, Bs, Es

def renumber(Ws, Bs, Es):
    W_old2new = dict()
    B_old2new = dict()
    for i, w in enumerate(Ws):
        W_old2new[w] = i
    for i, b in enumerate(Bs, len(Ws)):
        B_old2new[b] = i
    newEs = []
    for w, b in Es:
        newEs.append((W_old2new[w], B_old2new[b]))
    newWs = list(range(len(Ws)))
    newBs = list(range(len(Ws), len(Ws) + len(Bs)))
    return newWs, newBs, newEs

def solve(N, M, Ws, Bs, Es):
    '''
    貪欲に、並んでwbのペアをとれるだけ取る。-> 二部マッチングで求める。
    残りのバラバラのをペアにする。
    w のみ or b のみを食べる。
    '''
    Ws, Bs, Es = renumber(Ws, Bs, Es)
    nw = len(Ws)
    nb = len(Bs)
    connected_pair = bp_match(Ws, Bs, Es)
    unconnected_pair = min(nw, nb) - connected_pair
    single = nw + nb - min(nw, nb) * 2
    return 100 * connected_pair + 10 * unconnected_pair + 1 * single

N, M, Ws, Bs, Es = read_data()
print(solve(N, M, Ws, Bs, Es))
0