[BZOJ1583] [Usaco2009 Mar]Moon Mooing 哞哞叫(队列)
思想有点像蚯蚓那个题
#include <cstdio> #define N 4000001 #define LL long long #define min(x, y) ((x) < (y) ? (x) : (y)) #define max(x, y) ((x) > (y) ? (x) : (y)) LL q1[N], q2[N]; LL a1, b1, d1, a2, b2, d2; int n, h1 = 1, t1 = 1, h2 = 1, t2; int main() { int i; LL x, x1, x2; scanf("%lld %d", &q1[1], &n); scanf("%lld %lld %lld", &a1, &b1, &d1); scanf("%lld %lld %lld", &a2, &b2, &d2); while(n--) { x = ~(1 << 31); x <<= 32; if(h1 <= t1) x = min(x, q1[h1]); if(h2 <= t2) x = min(x, q2[h2]); if(h1 <= t1 && x == q1[h1]) h1++; if(h2 <= t2 && x == q2[h2]) h2++; x1 = a1 * x / d1 + b1; x2 = a2 * x / d2 + b2; if(min(x1, x2) > q1[t1]) q1[++t1] = min(x1, x2); if(max(x1, x2) > q2[t2]) q2[++t2] = max(x1, x2); else if(max(x1, x2) > q1[t1]) q1[++t1] = max(x1, x2); } printf("%lld\n", x); return 0; }
来自洛谷的更简便的题解
#include <cstdio> #include <iostream> typedef unsigned long long ull; //注意本题要用unsigned long long。 const int N = 4000000; ull a[N+5]; //这里我们将a数组看成一个队列 inline ull mn(ull x, ull y) { return x < y ? x : y; } int main() { int c, n, a1, b1, d1, a2, b2, d2, i = 1, f1 = 1, f2 = 1; scanf("%d%d%d%d%d%d%d%d", &c, &n, &a1, &b1, &d1, &a2, &b2, &d2); a[i++] = c; //初始元素c入队 while(i <= N) { ull x = mn(a1*a[f1]/d1+b1, a2*a[f2]/d2+b2); //取F1()和F2()中的较小值 a[i++] = x; //将该较小值入队 if(x == a1*a[f1]/d1+b1) f1++; //如果较小值来自F1(),则将F1()的指针f1+1。 if(x == a2*a[f2]/d2+b2) f2++; //如果较小值来自F2(),则将F2()的指针f2+1 } //重点理解while循环的内容。因为算出的F1()或F2()的数据单调递增,所以可以用这样的方式生成整个数列 std::cout << a[n]; //最后输出即可。 return 0; } //祝各位早日AC此题!