QOJ.ac

QOJ

IDProblemSubmitterResultTimeMemoryLanguageFile sizeSubmit timeJudge time
#85800#5664. Printing Stickershos_lyricTL 11819ms7276kbC++149.1kb2023-03-08 15:45:252023-03-08 15:45:29

Judging History

你现在查看的是最新测评结果

  • [2023-08-10 23:21:45]
  • System Update: QOJ starts to keep a history of the judgings of all the submissions.
  • [2023-03-08 15:45:29]
  • 评测
  • 测评结果:TL
  • 用时:11819ms
  • 内存:7276kb
  • [2023-03-08 15:45:25]
  • 提交

answer

#include <cassert>
#include <cmath>
#include <cstdint>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <algorithm>
#include <bitset>
#include <complex>
#include <deque>
#include <functional>
#include <iostream>
#include <limits>
#include <map>
#include <numeric>
#include <queue>
#include <set>
#include <sstream>
#include <string>
#include <unordered_map>
#include <unordered_set>
#include <utility>
#include <vector>

using namespace std;

using Int = long long;

template <class T1, class T2> ostream &operator<<(ostream &os, const pair<T1, T2> &a) { return os << "(" << a.first << ", " << a.second << ")"; };
template <class T> ostream &operator<<(ostream &os, const vector<T> &as) { const int sz = as.size(); os << "["; for (int i = 0; i < sz; ++i) { if (i >= 256) { os << ", ..."; break; } if (i > 0) { os << ", "; } os << as[i]; } return os << "]"; }
template <class T> void pv(T a, T b) { for (T i = a; i != b; ++i) cerr << *i << " "; cerr << endl; }
template <class T> bool chmin(T &t, const T &f) { if (t > f) { t = f; return true; } return false; }
template <class T> bool chmax(T &t, const T &f) { if (t < f) { t = f; return true; } return false; }


template <class Flow> struct MaxFlow {
  // Watch out when using types other than int and long long.
  static constexpr Flow FLOW_EPS = 1e-10L;
  static constexpr Flow FLOW_INF = std::numeric_limits<Flow>::max();
  
  int n, m;
  vector<int> ptr, nxt, zu;
  vector<Flow> capa;

  explicit MaxFlow(int n_) : n(n_), m(0), ptr(n_, -1) {}
  void ae(int u, int v, Flow w0, Flow w1 = 0) {
    assert(0 <= u); assert(u < n);
    assert(0 <= v); assert(v < n);
    assert(0 <= w0);
    assert(0 <= w1);
    nxt.push_back(ptr[u]); zu.push_back(v); capa.push_back(w0); ptr[u] = m++;
    nxt.push_back(ptr[v]); zu.push_back(u); capa.push_back(w1); ptr[v] = m++;
  }

  vector<int> see, lev, que;

  Flow augment(int u, int t, Flow limFlow) {
    if (u == t) return limFlow;
    for (int &i = see[u]; ~i; i = nxt[i]) if (capa[i] > FLOW_EPS) {
      const int v = zu[i];
      if (lev[u] < lev[v]) {
        const Flow f = augment(v, t, min(limFlow, capa[i]));
        if (f > FLOW_EPS) { capa[i] -= f; capa[i ^ 1] += f; return f; }
      }
    }
    return 0;
  }
  bool bfs(int s, int t) {
    for (int u = 0; u < n; ++u) { see[u] = ptr[u]; lev[u] = -1; }
    auto head = que.begin(), tail = que.begin();
    for (lev[*tail++ = s] = 0; head != tail; ) {
      const int u = *head++;
      for (int i = ptr[u]; ~i; i = nxt[i]) if (capa[i] > FLOW_EPS) {
        const int v = zu[i];
        if (!~lev[v]) {
          lev[*tail++ = v] = lev[u] + 1;
          if (v == t) return true;
        }
      }
    }
    return false;
  }
  Flow run(int s, int t, Flow limFlow = FLOW_INF) {
    see.resize(n); lev.resize(n); que.resize(n);
    Flow flow = 0;
    for (; flow + FLOW_EPS < limFlow && bfs(s, t); ) {
      for (Flow f; (f = augment(s, t, limFlow - flow)) > FLOW_EPS; flow += f) {}
    }
    return flow;
  }
};

////////////////////////////////////////////////////////////////////////////////


vector<int> uf;
int root(int u) {
  return (uf[u] < 0) ? u : (uf[u] = root(uf[u]));
}
bool connect(int u, int v) {
  u = root(u);
  v = root(v);
  if (u == v) return false;
  if (uf[u] > uf[v]) swap(u, v);
  uf[u] += uf[v];
  uf[v] = u;
  return true;
}


// undirected weighted graph
// costs[i]: separate ss[i] from others (ss[j] (i != j))
// ss should be distinct
template <class Flow> struct IsolatingCut {
  int n;
  vector<pair<pair<int, int>, Flow>> edges;

  IsolatingCut(int n_) : n(n_) {}
  void ae(int u, int v, Flow w) {
    assert(0 <= u); assert(u < n);
    assert(0 <= v); assert(v < n);
    edges.emplace_back(make_pair(u, v), w);
  }
  vector<Flow> run(const vector<int> &ss) {
    const int ssLen = ss.size();
    vector<int> is(n, 0);
    for (int e = 0; 1 << e < ssLen; ++e) {
      MaxFlow<Flow> mf(n + 2);
      for (int i = 0; i < ssLen; ++i) {
        if (i >> e & 1) {
          mf.ae(ss[i], n + 1, mf.FLOW_INF);
        } else {
          mf.ae(n, ss[i], mf.FLOW_INF);
        }
      }
      for (const auto &edge : edges) {
        mf.ae(edge.first.first, edge.first.second, edge.second, edge.second);
      }
      mf.run(n, n + 1);
      for (int u = 0; u < n; ++u) if (!~mf.lev[u]) is[u] |= 1 << e;
    }
    vector<int> ns(ssLen << 1, 0);
    vector<int> ids(n, -1);
    for (int u = 0; u < n; ++u) ids[u] = ns[is[u]]++;
    vector<vector<pair<pair<int, int>, Flow>>> ess(ssLen << 1);
    for (const auto &edge : edges) {
      const int u = edge.first.first;
      const int v = edge.first.second;
      const Flow w = edge.second;
      if (is[u] == is[v]) {
        ess[is[u]].emplace_back(make_pair(ids[u], ids[v]), w);
      } else {
        // with contracted vertex
        ess[is[u]].emplace_back(make_pair(ids[u], ns[is[u]]), w);
        ess[is[v]].emplace_back(make_pair(ids[v], ns[is[v]]), w);
      }
    }
    vector<Flow> costs(ssLen);
    for (int i = 0; i < ssLen; ++i) {
      assert(is[ss[i]] == i);
      MaxFlow<Flow> mf(ns[i] + 1);
      for (const auto &e : ess[i]) {
        mf.ae(e.first.first, e.first.second, e.second, e.second);
      }
      costs[i] = mf.run(ids[ss[i]], ns[i]);
    }
    return costs;
  }
};


constexpr int INF = 1001001001 / 2;

char buf[20010];

int M, N, H, V;
vector<string> A, B;
vector<vector<int>> D;

int main() {
  for (int numCases; ~scanf("%d", &numCases); ) { for (int caseId = 1; caseId <= numCases; ++caseId) {
    scanf("%d%d%d%d", &M, &N, &H, &V);
    A.resize(M);
    for (int x = 0; x < M; ++x) {
      scanf("%s", buf);
      A[x] = buf;
    }
    B.resize(M);
    for (int x = 0; x < M; ++x) {
      scanf("%s", buf);
      B[x] = buf;
    }
    D.assign(M, vector<int>(N));
    for (int x = 0; x < M; ++x) for (int y = 0; y < N; ++y) {
      scanf("%d", &D[x][y]);
    }
    
    uf.assign(M * (2 * N) + 1, -1);
    vector<vector<vector<int>>> usss(M + 1, vector<vector<int>>(N + 1));
    for (int x = 0; x < M; ++x) for (int y = 0; y < N; ++y) {
      const int u = x * (2 * N) + 2 * y + 0;
      const int v = x * (2 * N) + 2 * y + 1;
      const bool bu = (B[x][2 * y + 0] == '#');
      const bool bv = (B[x][2 * y + 1] == '#');
      if (A[x][y] == '/') {
        if (bu) {
          usss[x + 0][y + 0].push_back(u);
          usss[x + 0][y + 1].push_back(u);
          usss[x + 1][y + 0].push_back(u);
        }
        if (bv) {
          usss[x + 0][y + 1].push_back(v);
          usss[x + 1][y + 0].push_back(v);
          usss[x + 1][y + 1].push_back(v);
        }
      } else {
        if (bu) {
          usss[x + 0][y + 0].push_back(u);
          usss[x + 1][y + 0].push_back(u);
          usss[x + 1][y + 1].push_back(u);
        }
        if (bv) {
          usss[x + 0][y + 0].push_back(v);
          usss[x + 0][y + 1].push_back(v);
          usss[x + 1][y + 1].push_back(v);
        }
      }
    }
    for (int x = 0; x <= M; ++x) for (int y = 0; y <= N; ++y) if (!usss[x][y].empty()) {
      const int u = usss[x][y][0];
      for (const int v : usss[x][y]) {
        connect(u, v);
      }
    }
    
    vector<int> rs;
    for (int x = 0; x < M; ++x) for (int z = 0; z < 2 * N; ++z) if (B[x][z] == '#') {
      const int u = x * (2 * N) + z;
      if (uf[u] < 0) {
        rs.push_back(u);
      }
    }
// cerr<<"rs = "<<rs<<endl;
// for(int x=0;x<M;++x){for(int z=0;z<2*N;++z)fprintf(stderr,"%3d ",root(x*(2*N)+z));cerr<<endl;}
    
    IsolatingCut<int> ic(M * (2 * N) + 1);
    auto ae = [&](int x0, int z0, int x1, int z1, int c) -> void {
      const int u = root(x0 * (2 * N) + z0);
      const int v = root(x1 * (2 * N) + z1);
      const int cc = (B[x0][z0] != '#' && (x1 == M || B[x1][z1] != '#')) ? c : INF;
      if (u != v) {
        ic.ae(u, v, cc);
      }
    };
    for (int x = 0; x < M; ++x) for (int y = 0; y < N; ++y) {
      if (x + 1 < M) {
        ae(
          x    , 2 * y + ((A[x    ][y] == '/') ? 1 : 0),
          x + 1, 2 * y + ((A[x + 1][y] == '/') ? 0 : 1),
          H
        );
      }
      if (y + 1 < N) {
        ae(
          x, 2 *  y      + 1,
          x, 2 * (y + 1) + 0,
          V
        );
      }
    }
    for (int y = 0; y < N; ++y) {
      ae(
        0, 2 * y + ((A[0][y] == '/') ? 0 : 1),
        M, 0,
        H
      );
      ae(
        M - 1, 2 * y + ((A[M - 1][y] == '/') ? 1 : 0),
        M, 0,
        H
      );
    }
    for (int x = 0; x < M; ++x) {
      ae(
        x, 2 * 0 + 0,
        M, 0,
        V
      );
      ae(
        x, 2 * (N - 1) + 1,
        M, 0,
        V
      );
    }
    for (int x = 0; x < M; ++x) for (int y = 0; y < N; ++y) {
      ae(
        x, 2 * y + 0,
        x, 2 * y + 1,
        D[x][y]
      );
    }
    
    rs.push_back(M * (2 * N));
    auto ans = ic.run(rs);
    ans.pop_back();
    
    sort(ans.begin(), ans.end());
    const int ansLen = ans.size();
    printf("%d\n", ansLen);
    for (int h = 0; h < ansLen; ++h) {
      if (h) printf(" ");
      printf("%d", ans[h]);
    }
    puts("");
  }
#ifndef LOCAL
  break;
#endif
  }
  return 0;
}

Details

Tip: Click on the bar to expand more detailed information

Test #1:

score: 100
Accepted
time: 2ms
memory: 3584kb

input:

1
4 9 10 10
\////\\/\
\\/\//\//
//\\/\\/\
\///\//\/
.....#...##.......
.##.#.....##...##.
...#.##....####...
..#.........#..##.
1 1 1 1 1 1 1 1 1
1 1 1 1 1 1 1 1 1
1 1 1 1 1 1 1 1 1
1 1 1 1 1 1 1 1 1

output:

2
86 106

result:

ok 2 lines

Test #2:

score: 0
Accepted
time: 0ms
memory: 3648kb

input:

1
8 12 20 19
\//\//\/\\\/
//\/\\\/////
///\/\\\\//\
\//\\\/\/\/\
\\\\\///\///
///\\\\\\\\\
//\/////\\\\
/////\//////
........................
..##################....
..##..............##....
..##..######....##......
..##..##......####..##..
..##........##......##..
..############....####..
...........

output:

3
196 214 723

result:

ok 2 lines

Test #3:

score: 0
Accepted
time: 2ms
memory: 3660kb

input:

4
4 9 10 10
\////\\/\
\\/\//\//
//\\/\\/\
\///\//\/
.....#...##.......
.##.#.....##...##.
...#.##....####...
..#.........#..##.
1 1 1 1 1 1 1 1 1
1 1 1 1 1 1 1 1 1
1 1 1 1 1 1 1 1 1
1 1 1 1 1 1 1 1 1
8 12 20 19
\//\//\/\\\/
//\/\\\/////
///\/\\\\//\
\//\\\/\/\/\
\\\\\///\///
///\\\\\\\\\
//\/////\\\...

output:

2
86 106
3
196 214 723
3
104 159 537
1
42

result:

ok 8 lines

Test #4:

score: 0
Accepted
time: 6181ms
memory: 6752kb

input:

50
49 204 993 979
///\/\/\\\///\\//////\/\\\/\\\\//\\/\\\////\/\/\\\/\/\/\/\\/\/\/\///\/\\\//\///\/\\\\\/\//\\\\\\\\//\//\\\\\\//\///\///\\//\\/\/\\/\\/\\//\\\\\\/\\\//\/\////\\\\//\\////\\\/\///\/\//\\\//\///\\\/\\/\\\//\
\\//\\/\\///\//\\\\/\/\\\\\//\\/\/\////\\//\//\//\////\//\/\/\/\\\//\\////\//...

output:

26
4745 4847 5354 5486 5487 5697 5702 5715 5731 5739 5744 5784 5839 6654 7455 7677 7733 8463 9218 9578 10530 11334 12254 13358 16125 645597
583
4435 4444 4495 4497 4528 4537 4551 4563 4573 4577 4585 4603 4611 4643 4663 4686 4699 4711 4715 4745 4778 4851 5337 5362 5365 5389 5406 5416 5430 5436 5439 5...

result:

ok 100 lines

Test #5:

score: 0
Accepted
time: 4ms
memory: 3628kb

input:

50
6 3 993 979
///
\/\
/\\
\//
/\\
///
...#..
......
..#...
...##.
......
......
839 804 858
813 939 867
937 833 938
971 960 829
951 856 906
888 997 891
2 7 816 957
/\/\///
\/\\\//
.##..#...#....
.........#..#.
860 948 909 960 975 918 901
976 995 835 880 906 891 825
3 6 975 956
\\//\/
//\///
\\//\\
...

output:

2
5435 7646
3
5338 6210 8746
1
5275
2
5500 8373
3
5195 5202 7619
1
13672
1
9553
1
4517
2
5545 5626
2
5476 9891
1
15834
3
5381 5435 6302
1
5250
3
6282 6996 7945
3
6490 7661 9784
4
5594 5762 5810 5886
2
5675 14393
1
16122
4
5371 5391 5392 6195
4
5560 5627 7485 8423
2
5717 11501
3
4638 6238 9961
3
5350...

result:

ok 100 lines

Test #6:

score: 0
Accepted
time: 73ms
memory: 3928kb

input:

50
11 36 993 979
///\/\/\\\///\\//////\/\\\/\\\\//\\/
\\\////\/\/\\\/\/\/\/\\/\/\/\///\/\\
\//\///\/\\\\\/\//\\\\\\\\//\//\\\\\
\//\///\///\\//\\/\/\\/\\/\\//\\\\\\
/\\\//\/\////\\\\//\\////\\\/\///\/\
//\\\//\///\\\/\\/\\\//\\\//\\/\\///
\//\\\\/\/\\\\\//\\/\/\////\\//\//\/
/\////\//\/\/\/\\\//\\//...

output:

7
3968 3971 3973 3973 7914 9902 71559
5
1743 3448 3495 5323 53385
4
2013 11937 13816 55153
29
1663 1665 1682 1684 1688 1690 1699 1699 1745 1788 1863 3285 3311 3339 3345 3349 3384 3389 3440 3564 5026 5178 5216 6645 6672 6864 8470 11692 18685
17
1815 3447 5274 5367 6818 6912 7104 7143 8667 8866 8877 1...

result:

ok 100 lines

Test #7:

score: 0
Accepted
time: 11819ms
memory: 7276kb

input:

50
188 53 914 991
//\//////////////////////////////////////////////////
///////////////////\/////////////////\///////////////
/////////////////////////////////////////////////////
/////////\//////////////\////////////////////////////
/////////////////////////////////////////////////////
////////////...

output:

601
374 2004 2014 2017 2100 2102 2123 2133 2174 2183 2186 2192 2214 2271 2378 2450 2458 2483 2611 2723 3821 3821 3822 3823 3823 3825 3825 3825 3826 3826 3826 3826 3827 3827 3827 3827 3828 3828 3828 3828 3828 3829 3830 3830 3830 3830 3830 3830 3830 3830 3830 3831 3831 3831 3832 3832 3832 3832 3833 38...

result:

ok 100 lines

Test #8:

score: 0
Accepted
time: 372ms
memory: 6312kb

input:

50
41 243 995 824
/\///\\/\\\\///\/\/\////\//\////\/\/\/\\/\//\\/\/\//\//\////\\//\/\//\///\//\\//\\\//////\/\/\//\//\/\//\\/////\/\\//////\/\\///\\\/\\\///\\\/\//\//\//\\//\\\\\\\////\/\/\///\///\/\/\\\\/\/\///\///////\//\\//\\\/\///\\///\\/\/\//\//////\\/\\//
/\\\\\\\/\/////\//////\//\////\///\//\...

output:

1
526921
8
1967 3788 3795 3801 3827 3850 3883 338854
1
587397
1
373763
1
431602
1
366690
3
3480 3576 2212988
3
4017 4019 342820
3
1878 3556 645568
10
2080 3835 3838 3844 3846 3849 3959 5768 7600 384179
1
367560
1
351648
1
335366
1
337884
1
399771
2
3873 335759
19
1808 3435 3520 3548 3549 3554 3556 3...

result:

ok 100 lines

Test #9:

score: 0
Accepted
time: 3507ms
memory: 7240kb

input:

50
277 36 902 865
\/////\/\\\////\\/\\\\\/\\\\\\\\\/\\
/\\\\\\\\\/\\\\///\\\\/\\//\/\\//\//
\\\/\\\\////\\\//\\\\\/\\\\\\///\/\\
\\/\/\\\//\\\/\\\//\\//\\\/\\/\\\\\/
\/\\//\\\\\\\/\/\\\//\//\/\/\//\/\/\
//\\/\\/\\\\\\\\\/\\/\/\//\\\\\\\/\\
/\\\\\\\\\/\/\/\\\\\\\\/\\\///\/\\\/
///\\/\////\\\\\//\\\\\...

output:

9
1895 3620 3628 3630 3707 3717 5352 7165 505237
71
271 2015 2019 2027 2086 2093 2098 2101 2110 2110 2113 2118 2176 2184 2205 2274 2277 2291 2295 2381 2390 3849 3852 3852 3852 3853 3854 3857 3858 3864 3865 3933 3938 3939 3940 3941 3945 3947 3948 3951 3958 3960 3961 4013 4023 4032 4049 4065 4071 5693...

result:

ok 100 lines

Test #10:

score: 0
Accepted
time: 3192ms
memory: 6248kb

input:

50
23 434 9 9
////\////////\/\/////\//\///\/////////\/\////\/\////\\/\///////\///\//////\////////\////\/\/////\/\\/\/\//\/////////////\////\///\////\\/\////\/\///////////\\/////\//////\/\\//\\///////////\//\//////\/\//////////////////\\//////\/\//////////////\/////////\///////\///\\/\\/\/////////\\/...

output:

53
72 72 72 72 72 72 72 72 72 72 72 72 72 72 72 72 72 72 72 90 90 90 90 108 108 955 960 972 982 999 999 1016 1019 1023 1025 1026 1041 1048 1053 1062 1065 1068 1071 1071 1071 1071 1986 1995 2000 2034 9408 9537 28511
74
60 60 60 60 60 60 60 60 60 60 60 60 72 72 72 72 72 72 72 72 84 84 84 90 90 90 90 9...

result:

ok 100 lines

Test #11:

score: -100
Time Limit Exceeded

input:

50
49 204 10 990
///\//////\/////\//\///////////////////\/\////////////////\/////\/\/////\////\///////\/\/////////////////////////\/\////////////////\//////////////\/////\//////\//////////////\/\/\/////\//////////////\\//
//////////\/////////////////////////////////\/\\//\///\/////////////////\/////...

output:

291
2094 2099 2100 2102 2102 2105 2108 2110 2111 2111 2114 2114 2116 2116 2116 2120 2121 2123 2123 2125 2125 2126 2130 2131 2131 2131 2132 2134 2134 2134 2135 2135 2138 2138 2139 2139 2140 2140 2141 2141 2141 2141 2143 2143 2143 2144 2145 2147 2147 2148 2148 2148 2148 2150 2150 2150 2151 2151 2152 2...

result: