牛客练习赛32 A/B/C
https://ac.nowcoder.com/acm/contest/272/A
v<=k时 答案就是k个1
否则贪心的从中间向两边添加1
1 #include<bits/stdc++.h> 2 using namespace std; 3 #define LL long long 4 #define pii pair<int,int> 5 #define inf 0x3f3f3f3f 6 #define pb push_back 7 #define mp make_pair 8 const LL mod=1e9+7; 9 int s[200010]; 10 int main(){ 11 int v,k,i,j; 12 while(cin>>v>>k){ 13 s[0]=1; 14 s[v-1]=1; 15 for(i=(v-1)/2,j=1;j*2+2<=k;i--,j++){ 16 s[i]=1; 17 s[v-1-i]=1; 18 } 19 if(v<k){ 20 for(i=v;i<k;++i) s[i]=1; 21 v=k; 22 } 23 LL ans=0; 24 for(i=0;i<v;++i){ 25 ans=(ans*2+s[i])%mod; 26 } 27 cout<<ans<<endl; 28 } 29 return 0; 30 }
https://ac.nowcoder.com/acm/contest/272/B
考虑每一个点做出的贡献,通过这个点的路径数量是奇数就贡献一个A[u],否则就是0。
求每个点的路径数量时,只要dfs出所有子树的节点数量即可。
1 #include<bits/stdc++.h> 2 using namespace std; 3 #define LL long long 4 #define pii pair<int,int> 5 #define inf 0x3f3f3f3f 6 #define pb push_back 7 #define mp make_pair 8 const LL mod=1e9+7; 9 const int maxn=500050; 10 vector<int>g[maxn]; 11 LL A[maxn],n,ans=0; 12 int dfs(int u,int fa){ 13 int sum=0,s=0; 14 for(int i=0;i<g[u].size();++i){ 15 int v=g[u][i]; 16 if(v==fa) continue; 17 int tmp=dfs(v,u); 18 //s+=tmp; 19 sum+=(tmp*(s+1)); 20 s+=tmp; 21 //if(u==1)cout<<"sum= "<<sum<<" "<<s<<endl; 22 sum%=2; 23 } 24 sum+=((LL)n-s-1)*((LL)s+1); 25 sum%=2; 26 s++; 27 if(sum)ans^=A[u]; 28 return s; 29 } 30 int main(){ 31 int i,j,u,v; 32 scanf("%lld",&n); 33 for(i=1;i<n;++i){ 34 scanf("%d%d",&u,&v); 35 g[u].push_back(v); 36 g[v].push_back(u); 37 } 38 for(i=1;i<=n;++i)scanf("%lld",A+i); 39 dfs(1,0); 40 printf("%lld\n",ans); 41 return 0; 42 }
https://ac.nowcoder.com/acm/contest/272/C
观察发现n次操作之后白球个数的概率都是1/(n+1), 所以答案就是 1/(1+n) *(n+2)*(n+1)/2 = (n+2)/2
1 #include<bits/stdc++.h> 2 using namespace std; 3 int main(){ 4 int n; 5 scanf("%d",&n); 6 printf("%.7f\n",(2.0+n)/2); 7 return 0; 8 }