LDU20级新生排位赛第三场

pick一波出题人:

A

B

C

D

E

F

G

H

IJ

A. 小明的火柴

出题人题解

思路:

无论是组成矩形还是组成正方形,所需要的都是两条一样的边,甚至可能更多。

所以用map记录一下出现的次数,如果%4==2的话,就是两条一样的边。如果%4 == 0的话,就是四条一样的边。

最后判断一下就可以了。

int main(){
int n=read;
map<int,int>mp;
int cnt2=0,cnt4=0;
for(int i=1;i<=n;i++){
int x=read;
mp[x]++;
if(mp[x]%4==2) cnt2++;
if(mp[x]%4==0) cnt4++,cnt2--;
}
int m=read;
while(m--){
char op[4];
cin>>op;
int x=read;
if(op[0]=='+'){
mp[x]++;
if(mp[x]%4==2) cnt2++;
if(mp[x]%4==0) cnt4++,cnt2--;
}
else{
mp[x]--;
if(mp[x]%4==1) cnt2--;
if(mp[x]%4==3) cnt4--,cnt2++;
}
//cout<<cnt2<<" "<<cnt4<<endl;
if(cnt4>=2) puts("YES");
else if(cnt4==1&&cnt2>=2) puts("YES");
else puts("NO");

}
return 0;
}

B. Fox的阶乘

#include<bits/stdc++.h>
using namespace std;
#define
const int maxn=1e5+7;
int a[maxn];
int main()
{
int n;
int cnt=0;
cin>>n;
for(int i=1;i<=n;i++) a[i]=i;
for(int i=1;i<=n;i++)
{
if(a[i]%5==0)
{
while(a[i]%5==0)
{
a[i]/=5;
cnt++;
}
}
}

for(int i=1;i<=n;i++)
{
if(a[i]%2==0)
{
while(a[i]%2==0&&cnt>0)
{
a[i]/=2;
cnt--;
}
}
}
int sum=1;
for(int i=1;i<=n;i++)
{
sum=(sum*a[i])%10;
}

cout<<sum<<endl;
}

C. 如何优雅的筛筛筛

typedef long long ll;
const int N = 1e6 + 10;

int cnt;
int f[N];
bool vis[N];
int prime[N];

void init(const int n) {
f[1] = 1;
for (int i = 2; i <= n; i++) {
if (!vis[i]) {
f[i] = i;
prime[++cnt] = i;
}
for (int j = 1; j <= cnt && i <= n / prime[j]; j++) {
vis[i * prime[j]] = 1;
if (i % prime[j] == 0) {
f[i * prime[j]] = f[i];
break;
}
f[i * prime[j]] = f[i] * f[prime[j]];
}
}
}

int main() {

init(1e6);

int n; scanf("%d", &n);

for (int i = 1; i <= n; i++) printf("%d ", f[i]);
return 0;
}

D. 如何优雅的写代码

暴力能过,字典树也可以。

E. 小明同学喜欢的数

出题人题解

我的题解

F. 最简单的签到题

单点修改,区间求和。

树状数组or线段树。

G. 生日聚会

出题人题解

double cnt,sum,ans;
int main()
{
double n;
cin>>n;
ans=1.0;
cnt=1.0;
while(ans>=0.5000)
{
ans*=(1-cnt/n);
cnt++;
}
cout<<cnt-1<<endl;
return 0;
}

H. 光签题

思路:

考虑每个点的贡献,假设该点的度数为x,那么该点的贡献为x*(x-1)/2。

度数为x说明和该点相邻的点有x个,从这x点中任选两个都是满足题意的,根据组合数学原理可知答案。

代码:

int n;
int in[maxn];
int main(){
scanf("%d",&n);
int a,b;
for(int i=1;i<n;i++){
scanf("%d%d",&a,&b);
in[a]++;
in[b]++;
}
ll ans=0;
for(int i=1;i<=n;i++){
ans+=(in[i]*(in[i]-1))/2;
}
printf("%lld\n",ans);
}

I. Cutele’s 01 strings

出题人题解

J. 许个愿吧!

出题人题解