LA 3667 Ruler

https://icpcarchive.ecs.baylor.edu/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=1668

  这题想了两天,两天里经历了发烧感冒,各种疲惫难堪。

  因为这题在网上没有题解,只好强迫着自己去想应该怎么去搜索来解决。其实很容易就留意到答案的长度最多是7,实际上最多只需要找6个数,这个相当的关键。然后留意的一个要点是,距离是怎么测的呢?显然,一个长度是通过两个标记的距离差测出来的,所以对某个序列其中一个标记加或减这个长度,就会得到另一个标记,从而可以通过搜索6!*2种排列方式找到答案。而不是google能搜到的唯一的,而且还是没过的题解中解释的那样,标记不一定都是长度的其中几个。例如,5,15,25,35这组数据。

  我的搜索是用bfs的,可是写的有点复杂。最可惜的是,我写完以后,发现LA的这题无论怎么交都是PE。。。囧。表示最近比较倒霉!希望到时OJ弄好这个问题以后可以通过这个代码。现在先发上来:

View Code
  1 /***************** Written By Lyon, From SCAU, Beta 1.4.0 **************/
  2 /**************** headers && constants && definitions ****************/
  3 #pragma comment(linker, "/STACK:102400000,102400000")
  4 
  5 #include <cstdio>
  6 #include <cmath>
  7 #include <cstdlib>
  8 #include <cstring>
  9 #include <iomanip>
 10 #include <iostream>
 11 #include <algorithm>
 12 #include <numeric>
 13 #include <vector>
 14 #include <string>
 15 #include <bitset>
 16 #include <queue>
 17 #include <ctime>
 18 #include <stack>
 19 #include <set>
 20 #include <map>
 21 
 22 using namespace std;
 23 
 24 #define PB push_back
 25 #define FI first
 26 #define SE second
 27 #define MPR make_pair
 28 #define REP(i, n) for (int i = 0; i < (n); i++)
 29 #define REP_1(i, n) for (int i = 1; i <= (n); i++)
 30 #define INC(i, a, b) for (int i = (a); i <= (b); i++)
 31 #define DEC(i, a, b) for (int i = (a); i >= (b); i--)
 32 #define _clr(x) memset(x, 0, sizeof(x))
 33 #define _rst(x) memset(x, -1, sizeof(x))
 34 #define SZ(x) ((int) x.size())
 35 #define PRIQ priority_queue
 36 #define MSET multiset
 37 #define ITOR iterator
 38 #define RITOR reverse_iterator
 39 #define ALL(x) (x).begin(), (x).end()
 40 
 41 typedef long long LL;
 42 typedef unsigned long long ULL;
 43 typedef pair<int, int> PII;
 44 typedef pair<double, double> PDBDB;
 45 typedef pair<double, int> PDBI;
 46 typedef pair<int, double> PIDB;
 47 typedef vector<PIDB> VPIDB;
 48 typedef vector<PDBDB> VPDBDB;
 49 typedef vector<PDBI> VPDBI;
 50 typedef pair<PII, int> PIII;
 51 typedef pair<PII, string> PIIS;
 52 typedef vector<int> VI;
 53 typedef vector<LL> VL;
 54 typedef vector<PII> VPII;
 55 typedef vector<PIII> VPIII;
 56 typedef vector<double> VDBL;
 57 typedef vector<string> VSTR;
 58 typedef vector<VSTR> VVSTR;
 59 typedef vector<VI> VVI;
 60 typedef vector<char> VCH;
 61 typedef vector<VCH> VVCH;
 62 typedef vector<bool> VBL;
 63 typedef long double LDB;
 64 
 65 const int N = 1e6 + 500;
 66 const int M = 1 << 5;
 67 const int LEN = 105;
 68 const int hashMod = 1e6 + 5;
 69 const int inf = 0x55555555;
 70 const double eps = 1e-8;
 71 const LDB leps = 1e-10;
 72 const LL linf = 0x5555555555555555ll;
 73 const double finf = 1e50;
 74 const double pi = acos(-1.0);
 75 const int mod = 1e9 + 7;
 76 
 77 template <class T> inline T sqr(T x) {
 78     return x * x;
 79 }
 80 /*********************************************************************/
 81 
 82 typedef pair<char, VI> PCHVI;
 83 queue<PCHVI> Q;
 84 PCHVI best;
 85 int rec[55], n, id[N];
 86 bool vis[55];
 87 
 88 void getBest(PCHVI &tmp) {
 89     if (~best.FI) {
 90         if (SZ(best.SE) == SZ(tmp.SE)) {
 91             sort(ALL(tmp.SE));
 92             if (*best.SE.rbegin() > *tmp.SE.rbegin()) best = tmp;
 93         } else {
 94             if (SZ(best.SE) > SZ(tmp.SE)) best = tmp;
 95         }
 96     } else best = tmp;
 97 }
 98 
 99 bool check(VI &tmp) {
100     int t;
101     REP(i, n) vis[i] = false;
102     REP(i, SZ(tmp)) {
103         REP(j, i) {
104             if (abs(tmp[i] - tmp[j]) >= N) continue;
105             t = id[abs(tmp[i] - tmp[j])];
106             if (t) vis[t - 1] = true;
107         }
108     }
109     REP(i, n) if (!vis[i]) return false;
110     return true;
111 }
112 
113 bool test(VI &tmp, int x) {
114     REP(i, SZ(tmp)) if (x == tmp[i]) return false;
115     return true;
116 }
117 
118 void bfs(int n) {
119     VI tmp;
120     PCHVI cur;
121     n = min(n, 6);
122     tmp.clear();
123     best = MPR((char) -1, tmp);
124     while (!Q.empty()) Q.pop();
125     tmp.PB(0);
126     Q.push(MPR(0, tmp));
127     while (true) {
128         if (Q.empty()) break;
129         int qn = SZ(Q);
130 //        cout << SZ(Q.front().SE) << endl;
131         bool found = false;
132         REP(i, qn) {
133             cur = Q.front();
134             Q.pop();
135             REP(j, n) {
136                 if (cur.FI & (1 << j)) continue;
137                 cur.FI ^= 1 << j;
138                 REP(k, SZ(cur.SE)) {
139                     int t = cur.SE[k] - rec[j];
140                     if (t > 0 && test(cur.SE, t)) {
141                         cur.SE.PB(t);
142                         if (check(cur.SE)) {
143                             getBest(cur);
144                             found = true;
145                         }
146                         Q.push(cur);
147                         cur.SE.pop_back();
148                     }
149                     t = cur.SE[k] + rec[j];
150                     if (test(cur.SE, t)) {
151                         cur.SE.PB(t);
152                         if (check(cur.SE)) {
153                             getBest(cur);
154                             found = true;
155                         }
156                         Q.push(cur);
157                         cur.SE.pop_back();
158                     }
159                 }
160                 cur.FI ^= 1 << j;
161             }
162         }
163         if (found) break;
164     }
165 }
166 
167 void work() {
168     _clr(id);
169     sort(rec, rec + n);
170     n = unique(rec, rec + n) - rec;
171     REP(i, n) {
172         id[rec[i]] = i + 1;
173     }
174     bfs(n);
175     sort(ALL(best.SE));
176     printf("%d\n", SZ(best.SE));
177     REP(i, SZ(best.SE)) {
178         if (i) putchar(' ');
179         printf("%d", best.SE[i]);
180     }
181     puts("");
182 }
183 
184 int main() {
185     int cas = 1;
186     while (~scanf("%d", &n) && n) {
187         REP(i, n) scanf("%d", &rec[i]);
188         printf("Case %d:\n", cas++);
189         work();
190     }
191     return 0;
192 }

  欢迎有优化方法的大神留言,小牛表示虚心接受!

UPD:

  Yeah!修复以后表示178ms过了!值得一做的好题!

——written by Lyon

原文地址:https://www.cnblogs.com/LyonLys/p/LA_3667_Lyon.html