SRM477

250pt:

题意:给定一块蜂巢状的N*M矩阵,每块六边形和周围6个六边形相邻,现在告诉你哪些是陆地,哪些是水,问水陆交界处的长度。

思路:直接模拟

code:

 1 #line 7 "Islands.cpp"
 2 #include <cstdlib>
 3 #include <cctype>
 4 #include <cstring>
 5 #include <cstdio>
 6 #include <cmath>
 7 #include <algorithm>
 8 #include <vector>
 9 #include <string>
10 #include <iostream>
11 #include <sstream>
12 #include <map>
13 #include <set>
14 #include <queue>
15 #include <stack>
16 #include <fstream>
17 #include <numeric>
18 #include <iomanip>
19 #include <bitset>
20 #include <list>
21 #include <stdexcept>
22 #include <functional>
23 #include <utility>
24 #include <ctime>
25 using namespace std;
26 
27 #define PB push_back
28 #define MP make_pair
29 
30 #define REP(i,n) for(i=0;i<(n);++i)
31 #define FOR(i,l,h) for(i=(l);i<=(h);++i)
32 #define FORD(i,h,l) for(i=(h);i>=(l);--i)
33 
34 typedef vector<int> VI;
35 typedef vector<string> VS;
36 typedef vector<double> VD;
37 typedef long long LL;
38 typedef pair<int,int> PII;
39 
40 
41 class Islands
42 {
43         public:
44         int beachLength(vector <string> S)
45         {
46              int ans = 0;
47              int n = S.size(), m = S[0].size(), p;
48              for (int i = 0; i < n; ++i)
49                 for (int j = 0; j < m; ++j){
50                      if (j > 0 && S[i][j] == '#' && S[i][j-1] == '.') ++ans;
51                      if (j > 0 && S[i][j] == '.' && S[i][j-1] == '#') ++ans;
52                      if (i == 0) continue;
53                      if (i & 1) p = j;
54                      else p = j - 1;
55                      if (p >= 0 && S[i][j] == '.' && S[i-1][p] == '#') ++ans;
56                      if (p >= 0 && S[i][j] == '#' && S[i-1][p] == '.') ++ans;  
57                      if (p + 1 < m && S[i][j] == '.' && S[i-1][p+1] == '#') ++ans;
58                      if (p + 1 < m && S[i][j] == '#' && S[i-1][p+1] == '.') ++ans; 
59                 }
60              return ans;
61         }
62   };   
View Code

500pt:

题意:给定最多200个正整数,问最多能组成多少个勾股数对。勾股数对定义:对于互质数对(a, b),存在c,使得a*a+b*b=c*c,

思路:隐蔽的二分图。

        很明显先求出勾股数对,那么接下来便是一个最大匹配了。

       不过,是二分图吗?

       对于奇数a与奇数b,由于互质,那么a^2+b^2必定是2的倍数,必然不存在c

       对于偶数a与偶数b,不互质显然不存在。 

  所以是个二分图,直接匹配即可

code:

 1 #line 7 "PythTriplets.cpp"
 2 #include <cstdlib>
 3 #include <cctype>
 4 #include <cstring>
 5 #include <cstdio>
 6 #include <cmath>
 7 #include <algorithm>
 8 #include <vector>
 9 #include <string>
10 #include <iostream>
11 #include <sstream>
12 #include <map>
13 #include <set>
14 #include <queue>
15 #include <stack>
16 #include <fstream>
17 #include <numeric>
18 #include <iomanip>
19 #include <bitset>
20 #include <list>
21 #include <stdexcept>
22 #include <functional>
23 #include <utility>
24 #include <ctime>
25 using namespace std;
26 #define PB push_back
27 #define MP make_pair
28 #define REP(i,n) for(i=0;i<(n);++i)
29 #define FOR(i,l,h) for(i=(l);i<=(h);++i)
30 #define FORD(i,h,l) for(i=(h);i>=(l);--i)
31 #define M0(a) memset(a, 0, sizeof(a))
32 typedef vector<int> VI;
33 typedef vector<string> VS;
34 typedef vector<double> VD;
35 typedef long long LL;
36 typedef pair<int,int> PII;
37 int match[210], g[210][210];
38 int n, m;
39 bool vis[210];
40 class PythTriplets
41 {
42         public:
43         vector<int> v1, v2;
44         void makePoint(string &S){
45              int tmp = 0;
46              for (int i = 0; i < S.size(); ++i)
47                 if (S[i] == ' '){
48                      if (tmp == 0) continue;
49                      if (tmp & 1) v1.push_back(tmp);
50                      else v2.push_back(tmp);
51                      tmp = 0;
52                 } else tmp = tmp * 10 + S[i] - 48;
53              if (tmp > 0){
54                      if (tmp & 1) v1.push_back(tmp);
55                      else v2.push_back(tmp);
56              }
57         }
58         LL gcd(LL a, LL b){
59               return b ? gcd(b, a % b) : a;
60         }
61         bool ok(long long a, long long b){
62               if (gcd(a, b) > 1) return false;
63               long long c = floor(sqrt(a * a + b * b + .0));
64               if (c * c < a * a + b * b) ++c;
65               if (a * a + b * b == c * c) return true;
66               return false;
67         }
68         bool search_path(int u){
69              for (int v = 0; v < m; ++v) if (g[u][v] && !vis[v]){
70                    vis[v] = true;
71                    if (match[v] == -1 || search_path(match[v])){
72                          match[v] = u;
73                          return true;
74                    }
75              }
76              return false;
77         }
78         int findMax(vector <string> stick)
79         {
80             v1.clear();
81             v2.clear();
82             string S = accumulate(stick.begin(), stick.end(), string(""));
83             makePoint(S);
84             n = v1.size();
85             m = v2.size();
86             M0(g);
87             for (int i = 0; i < n; ++i)
88                for (int j = 0; j < m; ++j)
89                   if (ok(v1[i], v2[j])) g[i][j] = true;//, cout << v1[i] <<  " " << v2[j] << endl;
90             int ans = 0;
91             memset(match, -1, sizeof(match));
92             for (int i = 0; i < n; ++i){
93                   M0(vis);
94                   if (search_path(i)) ++ ans;
95             }
96             return ans;
97         }
98 };
View Code
原文地址:https://www.cnblogs.com/yzcstc/p/3627023.html