満点で45位でした。
A:
実は全探索で枝刈りもすれば2^40も見なくてすむことが分かる(らしい)。探索むずすぎィ!
何でこんなの7分くらいで解けるんですか…
#include<stdio.h> #include<algorithm> using namespace std; char c[200][100]; char d[200][100]; long long e[200]; long long f[200]; int val[200]; int ans[200]; long long s[200]; long long t[200]; int ret=99999999; int n,m; void solve(int a,long long now){ if(a==m){ ret=min(ret,__builtin_popcountll(now)); return; } for(int i=0;i<n;i++)s[i]=(e[i]^now)%(1LL<<(a+1)); for(int i=0;i<n;i++)t[i]=f[i]%(1LL<<(a+1)); std::sort(s,s+n);std::sort(t,t+n); bool ok=true; for(int i=0;i<n;i++)if(s[i]!=t[i])ok=false; if(ok)solve(a+1,now); for(int i=0;i<n;i++)s[i]=(e[i]^(now+(1LL<<a)))%(1LL<<(a+1)); for(int i=0;i<n;i++)t[i]=f[i]%(1LL<<(a+1)); std::sort(s,s+n);std::sort(t,t+n); ok=true; for(int i=0;i<n;i++)if(s[i]!=t[i])ok=false; if(ok)solve(a+1,now+(1LL<<a)); } int main(){ int T; scanf("%d",&T); for(int t=0;t<T;t++){ int a,b; scanf("%d%d",&a,&b); n=a;m=b; for(int i=0;i<a;i++)scanf("%s",c[i]); for(int i=0;i<a;i++)scanf("%s",d[i]); for(int i=0;i<a;i++){ e[i]=f[i]=0LL; for(int j=0;j<b;j++){ e[i]*=2; if(c[i][j]=='1')e[i]++; f[i]*=2; if(d[i][j]=='1')f[i]++; } } std::sort(e,e+a); std::sort(f,f+a); ret=99999999; solve(0,0); printf("Case #%d: ",t+1); if(ret==99999999)printf("NOT POSSIBLE\n"); else printf("%d\n",ret); } }
B:
典型木DP。やるだけ。
#include<stdio.h> #include<algorithm> #include<vector> using namespace std; vector<int> g[2000]; int sz[2000]; int solve(int a,int b){ int ch=0; int v1=0; int v2=0; sz[a]=1; for(int i=0;i<g[a].size();i++){ if(g[a][i]==b)continue; ch++; int q=solve(g[a][i],a); sz[a]+=sz[g[a][i]]; if(v1<q){ v2=v1; v1=q; }else if(v2<q){ v2=q; } } if(ch==0)return 1; if(ch==1)return 1; else return v1+v2+1; } int main(){ int T; scanf("%d",&T); for(int t=0;t<T;t++){ int a; scanf("%d",&a); for(int i=0;i<a;i++)g[i].clear(); for(int i=0;i<a-1;i++){ int b,c; scanf("%d%d",&b,&c); b--;c--; g[b].push_back(c); g[c].push_back(b); } int ret=999999999; for(int i=0;i<a;i++){ for(int j=0;j<a;j++)sz[j]=0; int dat=solve(i,-1); // printf("%d: %d\n",i,a-dat); ret=min(ret,a-dat); } printf("Case #%d: %d\n",t+1,ret); } }
C:
(これは別解らしい)
まず、長さ30の順列でbad algorithmを使うとどういう分布にあるのか調べてみた。
#include<stdio.h> #include<algorithm> using namespace std; int time[30][30]; int perm[30]; int main(){ int t=1000000000; while(t--){ for(int i=0;i<30;i++){ perm[i]=i; } for(int i=0;i<30;i++){ int p=rand()%30; swap(perm[p],perm[i]); } for(int i=0;i<30;i++)time[i][perm[i]]++; } for(int i=0;i<30;i++){ for(int j=0;j<30;j++)printf("%9d ",time[i][j]); printf("\n"); } }
出てきた値で評価点決めてある程度評価点が高かったらBADじゃね?
#include<stdio.h> #include<algorithm> using namespace std; int data[30][30]= {{33334612,44693419,43633610,42586441,41570504,40601075,39657083,38756004, 37890660,37047771,36218100,35435674,34665264,33914813,33210992,32520321, 31838936,31200998,30566759,29975424,29395560,28838060,28279184,27753433, 27257311,26761717,26281587,25813095,25364480,24937113},{ 33337285,32651572,44050610,43011073,42013588,41028989,40086869,39196911, 38310237,37469085,36639048,35857048,35096805,34365292,33633298,32944809, 32283337,31637958,31011254,30406710,29818783,29246142,28715116,28194205, 27677448,27187480,26712039,26236162,25807795,25373052},{ 33331934,32659622,32016511,43458881,42457472,41473656,40545211,39635288, 38758285,37912354,37100630,36301712,35537736,34802589,34091667,33392287, 32719253,32078025,31451632,30848237,30260897,29709422,29158355,28624344, 28126038,27630793,27150253,26697930,26250142,25818844},{ 33327772,32677891,32052434,31434179,42923440,41940746,41015192,40101231, 39224818,38375338,37553043,36762665,36000141,35251790,34542502,33855051, 33194712,32529964,31907141,31301440,30724873,30165190,29618318,29096764, 28580790,28088856,27607474,27161803,26709642,26274800},{ 33337799,32694432,32080325,31487740,30915795,42429364,41476973,40573636, 39699457,38844091,38032911,37236545,36464328,35733235,35023033,34338601, 33668212,33009368,32387884,31786986,31190298,30643878,30096611,29573312, 29060504,28562817,28085267,27628884,27183141,26754573},{ 33332124,32711339,32116885,31530216,30981306,30446299,41958389,41069508, 40201150,39342540,38520689,37732219,36966759,36222746,35506076,34821665, 34155221,33503195,32880968,32271655,31708311,31135807,30585760,30057909, 29547898,29069062,28584557,28112914,27678370,27248463},{ 33335073,32731912,32146688,31583121,31040419,30514010,30005975,41577575, 40701178,39868378,39035993,38235780,37477156,36726898,36021034,35330780, 34659841,34020115,33393526,32788364,32209538,31643163,31090843,30569703, 30049660,29573389,29091602,28631370,28186642,27760274},{ 33336575,32756136,32180192,31644082,31105236,30595786,30106617,29627355, 41228146,40387217,39553650,38772487,38003222,37259684,36548723,35860767, 35187161,34533891,33921967,33315701,32737082,32168562,31616451,31092689, 30588423,30090416,29624708,29160157,28721177,28275740},{ 33325652,32765753,32227148,31699999,31180908,30691921,30220080,29743272, 29299600,40924692,40101551,39320697,38549503,37803173,37097150,36397366, 35738185,35091683,34457961,33851323,33280139,32704897,32166943,31637008, 31128478,30640362,30166667,29706574,29256911,28824404},{ 33343891,32788733,32254384,31753984,31248981,30771577,30308765,29852310, 29431080,29011258,40675218,39885390,39118216,38378707,37652948,36969594, 36302886,35649158,35032589,34428879,33831705,33272458,32732027,32202699, 31692352,31200609,30728746,30265690,29821374,29393792},{ 33332232,32817266,32296720,31805505,31318058,30862902,30415214,29997403, 29568087,29173441,28782124,40447638,39690956,38961681,38243118,37548299, 36885151,36218665,35612579,35022234,34430890,33856370,33319486,32781768, 32282812,31791137,31311198,30853857,30397826,29975383},{ 33330003,32818241,32329639,31863510,31411185,30958303,30532189,30113616, 29710512,29325157,28959580,28597338,40310825,39557693,38849022,38145904, 37483622,36841058,36214809,35607484,35021910,34461615,33928034,33388390, 32885303,32388894,31916249,31462500,31009822,30577593},{ 33332339,32856155,32376073,31923179,31485719,31054332,30645044,30252961, 29868406,29486559,29133637,28782355,28459570,40185291,39470234,38783484, 38107384,37463028,36842759,36231260,35657392,35092541,34538641,34015065, 33501961,33005051,32541407,32074667,31635668,31197838},{ 33329226,32870007,32420457,31983729,31562841,31158176,30769018,30393715, 30020964,29659735,29318098,28988747,28667607,28358457,40113880,39431790, 38757470,38116186,37479551,36897826,36293727,35741736,35177578,34664632, 34153797,33653878,33177434,32718856,32270716,31850166},{ 33333274,32893461,32463732,32042900,31644675,31262779,30894404,30523949, 30171885,29847632,29518990,29195444,28886056,28599552,28323661,40082593, 39429014,38786084,38165019,37541833,36966147,36395693,35859845,35337467, 34815176,34311525,33860582,33394175,32937551,32514902},{ 33338876,32910152,32506165,32109532,31739987,31365093,31016175,30672762, 30350646,30020562,29707866,29411325,29125063,28844423,28573907,28314113, 40119570,39473981,38853808,38243892,37647485,37091385,36555755,36018118, 35502039,35008661,34536089,34083820,33654663,33204087},{ 33331958,32936501,32550195,32178249,31828647,31479272,31151912,30828157, 30520247,30198846,29912294,29637200,29355922,29097645,28834436,28598030, 28361485,40191521,39556592,38956372,38372896,37818850,37275220,36732881, 36226502,35732465,35256938,34798962,34350350,33929455},{ 33327581,32959241,32606395,32246387,31912271,31594925,31280134,30984219, 30684503,30402471,30132477,29867745,29607204,29368632,29128024,28895563, 28670373,28452929,40302086,39697513,39110548,38540617,38001678,37476244, 36975358,36475236,36008095,35537219,35092824,34661508},{ 33329076,33000099,32650929,32317450,32015642,31718087,31421968,31136493, 30865742,30606091,30349314,30097799,29863250,29638442,29420505,29199744, 28985873,28784586,28602810,40456318,39875991,39318828,38769214,38242718, 37731265,37237150,36770166,36300761,35870905,35422784},{ 33329801,33015801,32703124,32414706,32111986,31841160,31576487,31300578, 31055300,30814216,30582090,30358631,30131872,29920526,29701196,29501522, 29329971,29141704,28951830,28778560,40673766,40098548,39555341,39023234, 38526713,38032787,37560245,37097742,36644506,36226057},{ 33335912,33032484,32768050,32489017,32224884,31967816,31723397,31480836, 31247428,31018462,30815647,30606652,30398681,30211833,30023932,29831895, 29665114,29494692,29336593,29168771,29031825,40926135,40358523,39855513, 39339000,38855419,38367772,37911521,37467394,37044802},{ 33337358,33064394,32812714,32576024,32332807,32097815,31875813,31663412, 31442345,31253388,31051414,30869068,30676931,30515557,30335452,30184428, 30016131,29860288,29724895,29583157,29432304,29298736,41229081,40714801, 40185462,39698787,39217053,38754273,38303472,37892640},{ 33328388,33098772,32873498,32652850,32434028,32238016,32043521,31851953, 31650469,31487683,31307745,31139138,30986783,30824793,30676076,30520980, 30381208,30249204,30101463,29993446,29864966,29743324,29634751,41567749, 41073554,40571172,40092112,39641633,39202805,38767920},{ 33337751,33123352,32923390,32736096,32561701,32392566,32201351,32035702, 31875316,31729970,31580512,31423451,31285098,31144742,31015965,30885859, 30750205,30650623,30525207,30417149,30315092,30206742,30105522,30008054, 41987343,41475342,40988305,40542702,40096013,39678879},{ 33345367,33158587,32995716,32833744,32671417,32522301,32375351,32236442, 32099829,31962434,31824366,31721794,31604755,31477526,31372767,31258393, 31155051,31056576,30955825,30860637,30773969,30686878,30607996,30515408, 30446182,42423213,41946864,41479743,41033309,40597560},{ 33333960,33189131,33061407,32917395,32803418,32678370,32553005,32433388, 32338872,32214206,32120414,32014463,31918783,31840629,31745898,31643090, 31557981,31481598,31401607,31322882,31248386,31179902,31111350,31047740, 30970142,30925016,42898982,42451942,42014282,41581761},{ 33328226,33231599,33122051,33018690,32921578,32828087,32745963,32651279, 32566338,32488593,32412592,32323248,32264248,32180514,32115072,32059704, 31977170,31929478,31861450,31807627,31740329,31695124,31638736,31586785, 31532379,31488228,31446989,43453980,43007388,42576555},{ 33340221,33264371,33184248,33122309,33045173,32997124,32934661,32880341, 32815186,32759472,32705024,32654855,32602185,32551937,32501185,32462247, 32420041,32377433,32329248,32302623,32258154,32217844,32185198,32145443, 32113734,32088440,32054948,32019537,44048719,43618099},{ 33332757,33292357,33268358,33240908,33198690,33154593,33132523,33096823, 33070963,33031327,33016356,32995658,32958607,32933948,32903348,32888689, 32868526,32840756,32827574,32799961,32790896,32771074,32755693,32737407, 32712155,32696071,32677810,32670199,32645785,44690188},{ 33322977,33337220,33328352,33338104,33337644,33334860,33330716,33332881, 33332351,33337031,33338627,33327234,33326474,33327252,33324899,33332432, 33330916,33335255,33342614,33335736,33336141,33330479,33332750,33338517, 33330221,33336027,33337862,33337332,33336328,33330768}}; int b[1000]; int main(){ int T; scanf("%d",&T); for(int t=0;t<T;t++){ int a;scanf("%d",&a); for(int i=0;i<a;i++){ scanf("%d",b+i); } long long val=0; for(int i=0;i<a;i++)val+=data[(int)((double)i/1000*30)][(int)((double)b[i]/1000*30)]; printf("Case #%d: ",t+1); //printf("%lld ",val); if(val>33600000000LL)printf("BAD\n"); else printf("GOOD\n"); } }
よーし投げるか。
…
Correct!
やったぜ。