2022 纪中集训 7.12
T1 GMOJ 3057. 电影票
将买变形金刚的人视作 \(+1\), 将买哈利波特的人视作 \(-1\)。
将模型转化为一个 \(\pm 1\) 序列,要求前缀和始终大于 \(0\)。
裸的卡特兰数。
利用卡特兰数的通项公式 $h_n = \frac{1}{n+1} C^n_{2n} $。
\(C\) 指组合数。
由于最大要计算 \(C^{5000}_{10000}\),所以要用高精度。
而且普通高精度会T飞,需要使用压位高精。
点击查看代码
#include <bits/stdc++.h>
using namespace std;
typedef long long LL;
const int N = 1000;
const int Mod = 10000;
struct Number
{
int s[N + 10];
} a, b, ans;
inline Number operator*(Number &t, int q)
{
Number c = {0};
int v = 0;
for (int i = N; i > 0; i--)
{
c.s[i] = t.s[i] * q + v;
v = c.s[i] / Mod;
c.s[i] %= Mod;
}
return c;
}
inline Number operator/(Number &t, int q)
{
Number c = {0};
int v = 0;
for (int i = 1; i <= N; i++)
{
int p = v * Mod + t.s[i];
c.s[i] = p / q;
v = p % q;
}
return c;
}
inline Number operator-(Number &t, Number b)
{
Number c = {0};
int v = 0;
for (int i = N; i > 0; i--)
{
if (t.s[i] - v >= b.s[i])
c.s[i] = t.s[i] - b.s[i] - v, v = 0;
else
c.s[i] = t.s[i] - b.s[i] - v + Mod, v = 1;
}
return c;
}
inline void output(Number &t)
{
int i = 1;
while (!t.s[i])
i++;
printf("%d", t.s[i]);
for (int j = i + 1; j <= N; j++)
{
int p = 4, w[5];
memset(w, 0, sizeof w);
do
{
w[p--] = t.s[j] % 10;
} while (t.s[j] /= 10);
for (int k = 1; k <= 4; k++)
printf("%d", w[k]);
}
printf("\n");
}
int main()
{
int n, m;
scanf("%d%d", &n, &m);
a.s[N] = b.s[N] = 1;
int i = 1, j = m + n;
while(i < m)
{
b = b * j, b = b / i;
i ++, j--;
}
a = b * j, a = a / i;
ans = a - b;
output(ans);
return 0;
}
T3 GMOJ 3360.【NOI2013模拟】苹果树
统计某区间内的不同数字个数可以使用莫队,那么统计树上路径中的不同数字个数则使用树上莫队。
要将树上的路径转化为序列可以使用欧拉序。
欧拉序类似于dfs序,只是欧拉在进入点的时候和回溯到这个点的时候都记录一次,而dfs序只在进入点时记录。
考虑如何取出 \(x\) 到 \(y\) 的路径。
临 \(st_i\) 为访问 \(i\) 时的时间, \(ed_i\) 为回溯到 \(i\) 时的时间。
设 $st_x < st_j $, 否则交换 \(x\) 和 \(y\) 即可。
当 \(\operatorname{LCA}(x, y) = x\) 时, \(x\) 和 \(y\) 在同一条链上,此时统计欧拉序中 \(st_x\) 和 \(st_y\) 中出现一次的数的个数, 出现两次就相当于没走过。
当 \(\operatorname{LCA}(x, y) \neq x\) 时,\(x\) 和 \(y\) 不在同一条链上,此时统计欧拉序中 \(ed_x\) 和 \(st_y\) 中间出现一次的个数,记得特判 \(\operatorname{LCA}(x, y)\)。
考虑如何解决色盲问题:
- 当 \(a = b\) , 不需要操作。
- 当 \(a \neq b\),且 \(u\) 到 \(v\) 的路径上既有 \(a\) 色又有 \(b\) 色时,答案需要减 \(1\),否则不需要操作。
莫队实现的时候要不够熟练,没有注意各数组含义,调死了。。。
点击查看代码
#include <bits/stdc++.h>
using namespace std;
const int N = 1e5 + 10;
int n, m;
int col[N];
struct Edge
{
int v, nxt, w;
} e[N * 2];
int head[N], idx = 0;
inline void add(int u, int v, int w = 0)
{
e[++idx].v = v, e[idx].w = w, e[idx].nxt = head[u], head[u] = idx;
}
struct Query
{
int l, r, a, b;
int lca;
int id, belong;
} q[N];
int ord[N], cnt, st[N], ed[N];
int fa[N][30], vis[N], dep[N];
void dfs(int u, int father)
{
vis[u] = 1, ord[++cnt] = u, st[u] = cnt;
fa[u][0] = father, dep[u] = dep[father] + 1;
for(int i=1;i<20;i++) fa[u][i] = fa[fa[u][i-1]][i-1];
for (int i = head[u]; i; i = e[i].nxt)
{
int v = e[i].v;
if(e[i].v == father) continue;
dfs(v,u);
}
ord[++cnt] = u, vis[u] = -1, ed[u] = cnt;
}
int LCA(int x,int y)
{
if(dep[x] < dep[y]) swap(x, y);
for(int i=19;i>=0;i--) if(dep[fa[x][i]] >= dep[y]) x = fa[x][i];
if(x == y) return x;
for(int i=19;i>=0;i--) if(fa[x][i] != fa[y][i]) x = fa[x][i], y = fa[y][i];
return fa[x][0];
}
bool cmp(const Query& x,const Query& y)
{
if(x.belong == y.belong) return x.r < y.r;
return x.belong < y.belong;
}
int ans[N], sum;
int t[N];
void change(int i)
{
if(vis[ord[i]] > 0)
{
if(!t[col[ord[i]]]) sum ++;
t[col[ord[i]]]++;
}
else
{
t[col[ord[i]]] --;
if(!t[col[ord[i]]]) sum--;
}
vis[ord[i]] = -vis[ord[i]];
}
int main()
{
scanf("%d%d", &n, &m);
for (int i = 1; i <= n; i++) scanf("%d", &col[i]);
for (int i = 1; i <= n; i++)
{
int u, v;
scanf("%d%d", &u, &v);
add(u, v), add(v, u);
}
dfs(e[head[0]].v, 0);
int Block = sqrt(cnt);
for(int i=1;i<=m;i++)
{
int u, v;
scanf("%d%d%d%d",&u,&v,&q[i].a,&q[i].b);
if(st[u] > st[v]) swap(u,v);
q[i].lca = LCA(u, v);
q[i].id = i;
if(q[i].lca == u) q[i].l = st[u], q[i].r = st[v];
else q[i].l = ed[u], q[i].r = st[v];
q[i].belong = (q[i].l - 1) / Block + 1;
}
sort(q+1,q+1+m,cmp);
for(int i=1;i<=n;i++) vis[i] = 1;
int l = 1, r = 0;
for(int i=1;i<=m;i++)
{
while(r < q[i].r) change(++r);
while(r > q[i].r) change(r--);
while(l < q[i].l) change(l++);
while(l > q[i].l) change(--l);
ans[q[i].id] = sum;
if(!t[col[q[i].lca]]) ans[q[i].id]++;
if(q[i].a != q[i].b)
{
t[col[q[i].lca]] ++;
if(t[q[i].a] && t[q[i].b]) ans[q[i].id] --;
t[col[q[i].lca]] --;
}
}
for(int i=1;i<=m;i++) printf("%d\n", ans[i]);
return 0;
}
T4 GMOJ 3362. 数数
考虑类似前缀和的方式,将问题转化为计算从 \(1\) 到 \(n\) 的优美的数的个数。
首先优美数各数位之和一定为偶数,这是一个很重要的优化,一下就可以排除一半的数。
暴力搜索各位是否要选,判断选了的数位之和是否为所有数位之和的一半即可。
由于最多只有 \(9\) 位数,所以每个数的复杂度为 \(O(2^9)=512\)。
这个方法可以通过 \(10^7\) 的数据,能得到 \(50\) 分。
考虑到最大数据范围只有 \(10^9\)。
我们以 \(10^6\) 或 \(10^7\) 为一块来分块打表,剩余部分暴力处理。
点击查看代码
#include <bits/stdc++.h>
using namespace std;
#pragma GCC optimize(2)
typedef unsigned long long LL;
const int N = 1005;
int biao[N] = {0,376413,
832547, 1288828, 1744956, 2196800, 2647716,
3090920, 3526440, 3951372, 4366880, 4823015,
5304766, 5797144, 6290672, 6782004, 7272530,
7758910, 8238396, 8710536, 9182258, 9638539,
10130918, 10610575, 11103529, 11590745, 12080513,
12565094, 13045216, 13523103, 13996047, 14452175,
14945703, 15438658, 15913605, 16403907, 16892727,
17371943, 17858307, 18339125, 18810719, 19262563,
19753895, 20241111, 20731414, 21199399, 21684697,
22170473, 22655525, 23128982, 23601310, 24052226,
24542752, 25032520, 25521340, 26006639, 26480512,
26967738, 27450344, 27929454, 28401296, 28844500,
29330880, 29815461, 30294677, 30780453, 31267680,
31727883, 32207445, 32681531, 33151141, 33586661,
34066147, 34546269, 35032633, 35517685, 36000291,
36479854, 36928875, 37398605, 37865237, 38290169,
38762309, 39240196, 39721014, 40194471, 40673581,
41147667, 41617398, 42050819, 42514127, 42929635,
43401357, 43874301, 44345895, 44818223, 45290065,
45759675, 46226307, 46689616, 47111407, 47567542,
48049293, 48541671, 49035199, 49526531, 50017057,
50503437, 50982923, 51455063, 51926786, 52408537,
52900916, 53398017, 53897101, 54395976, 54894264,
55390376, 55882154, 56370124, 56858336, 57350715,
57847816, 58346901, 58846682, 59346650, 59846494,
60345546, 60842736, 61337762, 61832643, 62326171,
62825256, 63325037, 63822618, 64321881, 64821477,
65319367, 65818159, 66315614, 66811192, 67302524,
67801399, 68301368, 68800631, 69295186, 69792675,
70292149, 70790949, 71286703, 71781713, 72272239,
72770527, 73270371, 73769968, 74267457, 74763402,
75261351, 75759527, 76256605, 76751555, 77237935,
77734047, 78233099, 78730989, 79230464, 79728413,
80220834, 80714563, 81209373, 81704149, 82183635,
82675413, 83172603, 83671395, 84170195, 84668372,
85162101, 85646750, 86134011, 86626601, 87098741,
87586711, 88081737, 88579192, 89074946, 89572024,
90066835, 90554096, 91029271, 91513942, 91985664,
92473876, 92968757, 93464335, 93959345, 94454295,
94949071, 95441662, 95926333, 96400455, 96856736,
97349115, 97828772, 98321726, 98808942, 99298710,
99783291, 100263413, 100741300, 101214244, 101706623,
102203724, 102702809, 103202590, 103702558, 104202402,
104701454, 105198644, 105693670, 106188552, 106668209,
107167293, 107654509, 108153408, 108643571, 109140447,
109631936, 110124934, 110615086, 111104170, 111597125,
112096906, 112595804, 113093027, 113592810, 114091415,
114589181, 115087418, 115585176, 116080738, 116567954,
117067923, 117558086, 118057868, 118549357, 119048442,
119540443, 120037757, 120529913, 121025141, 121514909,
122014753, 122511630, 123010235, 123509319, 124005151,
124504320, 124999107, 125496723, 125991518, 126476099,
126975151, 127466640, 127964407, 128456408, 128955576,
129444361, 129941988, 130432181, 130927549, 131407671,
131904861, 132397859, 132896096, 133393411, 133888198,
134385824, 134870790, 135365761, 135853348, 136331235,
136826261, 137316413, 137814171, 138306327, 138803944,
139294137, 139789107, 140268613, 140761869, 141234813,
141729694, 142218778, 142714340, 143209568, 143704363,
144199732, 144687319, 145180575, 145654892, 146111020,
146604548, 147097503, 147572450, 148062752, 148551572,
149030788, 149517152, 149997970, 150469564, 150963092,
151462177, 151961958, 152459539, 152958802, 153458398,
153956288, 154455080, 154952535, 155448113, 155941068,
156440849, 156939747, 157436970, 157936753, 158435358,
158933124, 159431361, 159929119, 160424682, 160899629,
161397209, 161894432, 162373648, 162870479, 163366196,
163847035, 164342307, 164834856, 165316242, 165806545,
166305808, 166805590, 167302421, 167797533, 168296439,
168794206, 169291181, 169787227, 170282583, 170771403,
171271000, 171769605, 172265321, 172764227, 173259685,
173756939, 174255102, 174749455, 175244787, 175724003,
176221893, 176719660, 177200499, 177698265, 178195519,
178676905, 179174053, 179669962, 180151503, 180637867,
181136659, 181634896, 182130169, 182627144, 183125306,
183622454, 184112942, 184610046, 185104838, 185585656,
186083111, 186580869, 187073418, 187569465, 188063818,
188559726, 189056830, 189540680, 190034891, 190506485,
191002063, 191497625, 191979011, 192474367, 192969700,
193451241, 193946033, 194440244, 194913068, 195364912,
195856244, 196343460, 196833763, 197301748, 197787046,
198272822, 198757874, 199231331, 199703659, 200194991,
200693866, 201193835, 201693098, 202187653, 202685142,
203184616, 203683416, 204179170, 204674180, 205161396,
205661365, 206151528, 206651310, 207142799, 207641884,
208133885, 208631199, 209123355, 209618583, 210108886,
210608149, 211107931, 211604762, 212099874, 212598780,
213096547, 213593522, 214089568, 214584925, 215052910,
215547464, 216038953, 216534065, 217007522, 217499718,
217990901, 218484410, 218959905, 219446727, 219932026,
220429515, 220928599, 221427505, 221919701, 222413231,
222911993, 223409872, 223904583, 224393574, 224879350,
225378825, 225870826, 226368592, 226859775, 227358537,
227847477, 228346119, 228838089, 229333643, 229818695,
230317495, 230814810, 231311785, 231805293, 232303172,
232801814, 233291625, 233787283, 234281777, 234755234,
235250988, 235743144, 236239191, 236714686, 237209396,
237701366, 238197024, 238673284, 239165608, 239637936,
240132946, 240628174, 241123530, 241610353, 242099344,
242594898, 243089392, 243581716, 244056062, 244506978,
244997504, 245487272, 245976092, 246461391, 246935264,
247422490, 247905096, 248384206, 248856048, 249346574,
249844862, 250344706, 250844303, 251341792, 251837737,
252335686, 252833862, 253330940, 253825890, 254315658,
254815502, 255312379, 255810984, 256310068, 256805900,
257305069, 257799856, 258297472, 258792267, 259281087,
259780684, 260279289, 260775005, 261273911, 261769369,
262266623, 262764786, 263259139, 263754471, 264239770,
264737259, 265236343, 265735249, 266227445, 266720975,
267219737, 267717616, 268212327, 268701319, 269175192,
269671136, 270166968, 270662426, 271155956, 271637394,
272132980, 272626656, 273118401, 273606213, 274093440,
274591389, 275090557, 275587811, 276086573, 276582159,
277074753, 277572087, 278069041, 278564272, 279046878,
279545055, 280039842, 280538004, 281035883, 281529559,
282026893, 282513143, 283009664, 283502662, 283981772,
284478850, 284976467, 285470820, 285965530, 286457275,
286954229, 287450750, 287934208, 288427696, 288899538,
289394488, 289889283, 290384616, 290873607, 291361419,
291856650, 292349648, 292843136, 293317366, 293760570,
294246950, 294731531, 295210747, 295696523, 296183750,
296643953, 297123515, 297597601, 298067211, 298553591,
299049703, 299548755, 300046645, 300546120, 301044069,
301536490, 302030219, 302525029, 303019805, 303504386,
304003438, 304494927, 304992694, 305484695, 305983863,
306472648, 306970275, 307460468, 307955836, 308435052,
308932942, 309430709, 309911548, 310409314, 310906568,
311387954, 311885102, 312381011, 312862552, 313348328,
313847803, 314339804, 314837570, 315328753, 315827515,
316316455, 316815097, 317307067, 317802621, 318289848,
318787797, 319286965, 319784219, 320282981, 320778567,
321271161, 321768495, 322265449, 322760681, 323220884,
323713304, 324202089, 324683475, 325172415, 325665009,
326128508, 326618472, 327104745, 327585453, 328065016,
328558745, 329056371, 329553519, 330052161, 330549495,
331039459, 331524705, 332017239, 332510934, 332985020,
333479831, 333970024, 334465932, 334957902, 335454856,
335941129, 336433663, 336912903, 337405293, 337874903,
338369679, 338865048, 339346589, 339842143, 340337374,
340818082, 341311777, 341804167, 342276694, 342712214,
343191700, 343671822, 344158186, 344643238, 345125844,
345605407, 346054428, 346524158, 346990790, 347470276,
347962054, 348459244, 348958036, 349456836, 349955013,
350448742, 350933391, 351420652, 351913242, 352393364,
352890554, 353383552, 353881789, 354379104, 354873891,
355371517, 355856483, 356351454, 356839041, 357325405,
357824197, 358322434, 358817707, 359314682, 359812844,
360309992, 360800480, 361297584, 361792376, 362277428,
362776228, 363273543, 363770518, 364264026, 364761905,
365260547, 365750358, 366246016, 366740510, 367223116,
367721293, 368216080, 368714242, 369212121, 369705797,
370203131, 370689381, 371185902, 371678900, 372158463,
372652192, 373149818, 373646966, 374145608, 374642942,
375132906, 375618152, 376110686, 376604382, 377053403,
377538051, 378023017, 378513505, 379003316, 379489566,
379974812, 380427196, 380908305, 381388631, 381858362,
382345623, 382840593, 383337697, 383833355, 384329876,
384822410, 385303519, 385778157, 386266143, 386732775,
387225366, 387712953, 388207745, 388702239, 389195237,
389688932, 390169258, 390657244, 391130374, 391555306,
392027446, 392505333, 392986151, 393459608, 393938718,
394412804, 394882535, 395315956, 395779264, 396251404,
396739374, 397234400, 397731855, 398227609, 398724687,
399219498, 399706759, 400181934, 400666605, 401144492,
401639518, 402129670, 402627428, 403119584, 403617201,
404107394, 404602364, 405081870, 405575126, 406055944,
406553399, 407051157, 407543706, 408039753, 408534106,
409030014, 409527118, 410010968, 410505179, 410978636,
411474390, 411966546, 412462593, 412938088, 413432798,
413924768, 414420426, 414896686, 415389010, 415868120,
416365198, 416862815, 417357168, 417851878, 418343623,
418840577, 419337098, 419820556, 420314044, 420788130,
421282941, 421773134, 422269042, 422761012, 423257966,
423744239, 424236773, 424716013, 425208403, 425678134,
426165395, 426660365, 427157469, 427653127, 428149648,
428642182, 429123291, 429597929, 430085916, 430519337,
430994511, 431474017, 431957867, 432434127, 432917585,
433396825, 433871463, 434306086, 434779290, 435242599,
435727270, 436220526, 436714737, 437207061, 437700549,
438192939, 438680925, 439154129, 439626259, 440041767,
440513489, 440986433, 441458027, 441930355, 442402197,
442871807, 443338439, 443801748, 444223539, 444695261,
445183473, 445678354, 446173932, 446668942, 447163892,
447658668, 448151259, 448635930, 449110052, 449582996,
450077877, 450566961, 451062523, 451557751, 452052546,
452547915, 453035502, 453528758, 454003075, 454474669,
454970247, 455465809, 455947195, 456442551, 456937884,
457419425, 457914217, 458408428, 458881252, 459353580,
459848590, 460343818, 460839174, 461325997, 461814988,
462310542, 462805036, 463297360, 463771706, 464243548,
464738498, 465233293, 465728626, 466217617, 466705429,
467200660, 467693658, 468187146, 468661376, 469130986,
469625762, 470121131, 470602672, 471098226, 471593457,
472074165, 472567860, 473060250, 473532777, 473999409,
474492000, 474979587, 475474379, 475968873, 476461871,
476955566, 477435892, 477923878, 478397008, 478860317,
479344988, 479838244, 480332455, 480824779, 481318267,
481810657, 482298643, 482771847, 483243978, 483665769,
484139891, 484614208, 485087032, 485561378, 486035608,
486508135, 486981265, 487453395, 487875963};
int st[N];
LL a[N], cnt, ans;
int sum, flag;
inline void dfs(LL x, LL y)
{
if (2*y > sum) return;
if (x > cnt)
{
if (y == sum - y) ++ans, flag = 1;
return;
}
st[x] = 0;
dfs(x + 1, y);
if (flag) return;
st[x] = 1;
dfs(x + 1, y + a[x]);
}
inline LL solve(LL x)
{
if (x <= 10) return 0;
ans = biao[x / 1000000];
for (int i = x / 1000000 * 1000000 + 1; i <= x; i++)
{
cnt = sum = 0;
memset(st, 0, sizeof(st));
LL temp = i;
while (temp)
{
a[++cnt] = temp % 10;
sum += temp % 10;
temp /= 10;
}
if (sum & 1) continue;
flag = 0;
dfs(1, 0);
}
return ans;
}
int main()
{
register int l, r;
scanf("%d%d", &l, &r);
printf("%d\n", solve(r) - solve(l - 1));
}
// int main()
// {
// int ans = 0, cnt = 0;
// for (int i = 1; i <= 1000000000; i++)
// {
// ans += check(i);
// if (i % 1000000 == 0)
// {
// printf("%d,", ans);
// if (cnt % 5 == 0)
// putchar('\n');
// cnt++;
// }
// }
// cout << cnt;
// return 0;
// }