【HDU】2119 Matrix

  1 #include<cstdio>

  2 #include<cstring>

  3 #include<algorithm>

  4 #define MAXN 110

  5 #define MAXM 1000000

  6 #define INF 0x7FFFFFFF

  7 using namespace std;

  8 int G[MAXN][MAXN];

  9 int L[MAXM], R[MAXM], U[MAXM], D[MAXM];

 10 int size, ans, S[MAXM], H[MAXM], C[MAXM];

 11 bool vis[MAXN * 100];

 12 void Link(int r, int c)

 13 {

 14     U[size] = c;

 15     D[size] = D[c];

 16     U[D[c]] = size;

 17     D[c] = size;

 18     if (H[r] < 0)

 19         H[r] = L[size] = R[size] = size;

 20     else

 21     {

 22         L[size] = H[r];

 23         R[size] = R[H[r]];

 24         L[R[H[r]]] = size;

 25         R[H[r]] = size;

 26     }

 27     S[c]++;

 28     C[size++] = c;

 29 }

 30 void Remove(int c)

 31 {

 32     int i;

 33     for (i = D[c]; i != c; i = D[i])

 34     {

 35         L[R[i]] = L[i];

 36         R[L[i]] = R[i];

 37     }

 38 }

 39 void Resume(int c)

 40 {

 41     int i;

 42     for (i = D[c]; i != c; i = D[i])

 43         L[R[i]] = R[L[i]] = i;

 44 }

 45 int A()

 46 {

 47     int i, j, k, res;

 48     memset(vis, false, sizeof(vis));

 49     for (res = 0, i = R[0]; i; i = R[i])

 50     {

 51         if (!vis[i])

 52         {

 53             res++;

 54             for (j = D[i]; j != i; j = D[j])

 55             {

 56                 for (k = R[j]; k != j; k = R[k])

 57                     vis[C[k]] = true;

 58             }

 59         }

 60     }

 61     return res;

 62 }

 63 void Dance(int now)

 64 {

 65     if (R[0] == 0)

 66         ans = min(ans, now);

 67     else if (now + A() < ans)

 68     {

 69         int i, j, temp, c;

 70         for (temp = INF,i = R[0]; i; i = R[i])

 71         {

 72             if (temp > S[i])

 73             {

 74                 temp = S[i];

 75                 c = i;

 76             }

 77         }

 78         for (i = D[c]; i != c; i = D[i])

 79         {

 80             Remove(i);

 81             for (j = R[i]; j != i; j = R[j])

 82                 Remove(j);

 83             Dance(now + 1);

 84             for (j = L[i]; j != i; j = L[j])

 85                 Resume(j);

 86             Resume(i);

 87         }

 88     }

 89 }

 90 void Init(int m)

 91 {

 92     int i;

 93     for (i = 0; i <= m; i++)

 94     {

 95         R[i] = i + 1;

 96         L[i + 1] = i;

 97         U[i] = D[i] = i;

 98         S[i] = 0;

 99     }

100     R[m] = 0;

101     size = m + 1;

102 }

103 int main()

104 {

105     int n, m, i, j, k, r;

106     while (scanf("%d", &n), n)

107     {

108         scanf("%d", &m);

109         for (i = k = 0; i < n; i++)

110         {

111             for (j = 0; j < m; j++)

112             {

113                 scanf("%d", &G[i][j]);

114                 if (G[i][j])

115                     G[i][j] = ++k;

116             }

117         }

118         Init(k);

119         for (i = r = 0; i < n; i++)

120         {

121             H[++r] = -1;

122             for (j = 0; j < m; j++)

123             {

124                 if (G[i][j])

125                     Link(r, G[i][j]);

126             }

127         }

128         for (j = 0; j < m; j++)

129         {

130             H[++r] = -1;

131             for (i = 0; i < n; i++)

132             {

133                 if (G[i][j])

134                     Link(r, G[i][j]);

135             }

136         }

137         ans = min(n, m);

138         Dance(0);

139         printf("%d\n", ans);

140     }

141     return 0;

142 }

你可能感兴趣的:(Matrix)