RC-u1 大家一起查作弊 - 2024 睿抗机器人开发者大赛CAIP-编程技能赛-本科组(国赛) (pintia.cn)
思路:模拟题。第四题写的,扣了4分,不知道哪里有问题。
void solve(){ A 11/15
string str;
int ans=0,cnt=0,len=0;
string cur="";
while(getline(cin,str)){
int n=str.size();
for(int i=0;i<n;i++){
if(str[i]>='a'&&str[i]<='z'||str[i]>='A'&&str[i]<='Z'||str[i]>='0'&&str[i]<='9') cur+=str[i];
else if(cur!=""){
cnt++,len+=cur.size();
int nn=cur.size();
bool c1=false,c2=false,c3=false;
for(int f=0;f<nn;f++){
if(cur[f]>='a'&&cur[f]<'z') c1=true;
if(cur[f]>='A'&&cur[f]<='Z') c2=true;
if(cur[f]>='0'&&cur[f]<='9') c3=true;
}
if(c1&&c2&&c3) ans+=5;
else if(c1&&c3||c2&&c3) ans+=3;
else if(c1&&c2) ans+=1;
cur="";
}
}
if(cur!=""){
cnt++,len+=cur.size();
int nn=cur.size();
bool c1=false,c2=false,c3=false;
for(int f=0;f<nn;f++){
if(cur[f]>='a'&&cur[f]<'z') c1=true;
if(cur[f]>='A'&&cur[f]<='Z') c2=true;
if(cur[f]>='0'&&cur[f]<='9') c3=true;
}
if(c1&&c2&&c3) ans+=5;
else if(c1&&c3||c2&&c3) ans+=3;
else if(c1&&c2) ans+=1;
cur="";
}
}
if(cur!=""){
cnt++,len+=cur.size();
int nn=cur.size();
bool c1=false,c2=false,c3=false;
for(int f=0;f<nn;f++){
if(cur[f]>='a'&&cur[f]<'z') c1=true;
if(cur[f]>='A'&&cur[f]<='Z') c2=true;
if(cur[f]>='0'&&cur[f]<='9') c3=true;
}
if(c1&&c2&&c3) ans+=5;
else if(c1&&c3||c2&&c3) ans+=3;
else if(c1&&c2) ans+=1;
cur="";
}
cout<<ans<<endl<<len<<" "<<cnt;
}
RC-u2 谁进线下了?II - 2024 睿抗机器人开发者大赛CAIP-编程技能赛-本科组(国赛) (pintia.cn)
思路:这不省赛原题。。签到模拟。
int n;
pair<int,int> arr[35];
bool cmp(pair<int,int> a,pair<int,int> b){
if(a.first!=b.first) return a.first>b.first;
return a.second<b.second;
}
void solve(){ B
cin>>n;
for(int i=1;i<=30;i++) arr[i].second=i;
map<int,int> vis;
for(int i=1;i<=n;i++){
for(int j=1;j<=20;j++){
int c,p; cin>>c>>p;
vis[c]=1;
if(p==1) arr[c].first+=25;
else if(p==2) arr[c].first+=21;
else if(p==3) arr[c].first+=18;
else if(p==4) arr[c].first+=16;
else if(p==5) arr[c].first+=15;
else if(p==6) arr[c].first+=14;
else if(p==7) arr[c].first+=13;
else if(p==8) arr[c].first+=12;
else if(p==9) arr[c].first+=11;
else if(p==10) arr[c].first+=10;
else if(p==11) arr[c].first+=9;
else if(p==12) arr[c].first+=8;
else if(p==13) arr[c].first+=7;
else if(p==14) arr[c].first+=6;
else if(p==15) arr[c].first+=5;
else if(p==16) arr[c].first+=4;
else if(p==17) arr[c].first+=3;
else if(p==18) arr[c].first+=2;
else if(p==19) arr[c].first+=1;
else if(p==20) arr[c].first+=0;
}
}
sort(arr+1,arr+30+1,cmp);
for(int i=1;i<=30;i++){
if(vis[arr[i].second]==0) continue;
cout<<arr[i].second<<" "<<arr[i].first<<endl;
}
}
RC-u3 势均力敌 - 2024 睿抗机器人开发者大赛CAIP-编程技能赛-本科组(国赛) (pintia.cn)
思路:二进制枚举。复杂度没算,感觉不会T,的确没T。
int n;
int arr[5];
vector<int> p;
vector<int> vct;
int getnum(){
int num=0;
for(auto a:p){
num*=10;
num+=arr[a];
}
return num;
}
void solve(){ C
cin>>n;
for(int i=1;i<=n;i++) cin>>arr[i];
for(int i=1;i<=n;i++) p.emplace_back(i);
vct.emplace_back(getnum());
while(next_permutation(p.begin(),p.end())) vct.emplace_back(getnum());
int n0=1;
for(int i=n;i>=1;i--) n0*=i;
for(int i=0;i<(1ll<<n0);i++){
int cnta=0,cntb=0;
int suma=0,sumb=0;
vector<int> vcta;
for(int j=0;j<n0;j++){
if((i>>j)&1) cnta++,suma+=vct[j]*vct[j],vcta.emplace_back(vct[j]);
else cntb++,sumb+=vct[j]*vct[j];
}
if(cnta==cntb&&suma==sumb){
for(auto v:vcta) cout<<v<<endl;
return;
}
}
}
RC-u4 City 不 City - 2024 睿抗机器人开发者大赛CAIP-编程技能赛-本科组(国赛) (pintia.cn)
思路:数据只有1000,不用想这么多,直接枚举hot[i]就行,都不用改最短路。复杂度o(n*n*logn)。
正常写的话优先队列pq应该存三个值< <代价,温度>, to>,第一次写是这样写的,但是不知道为什么emplace_back()这三个值会报错。然后就直接写暴力了,没T。
int n,m,S,T;
vector<pair<int,int>> vct[1003];
int hot[1003];
priority_queue<pair<int,int>> pq;
int dis[1003];
bool vis[1003];
void dijkstra(int s,int maxhot){
for(int i=1;i<=n;i++) dis[i]=INT_MAX,vis[i]=0;
dis[S]=0;
pq.emplace(0,S);
while(pq.size()){
int from=pq.top().second;
pq.pop();
if(vis[from]) continue;
vis[from]=1;
for(auto v:vct[from]){
int to=v.first,w=v.second;
if(hot[to]>maxhot) continue;
if(dis[to]>dis[from]+w){
dis[to]=dis[from]+w;
pq.emplace(-dis[to],to);
}
}
}
}
void solve(){ D ö¾Ù
cin>>n>>m>>S>>T;
for(int i=1;i<=n;i++) cin>>hot[i];
bool check=false;
int ans=INT_MAX;
for(int i=1;i<=m;i++){
int u,v,w; cin>>u>>v>>w;
vct[u].emplace_back(v,w);
vct[v].emplace_back(u,w);
if(S==u&&T==v||T==u&&S==v) check=true,ans=min(ans,w);
}
hot[S]=0,hot[T]=0;
int ans2=INT_MAX,ans3=INT_MAX;
for(int i=1;i<=n;i++){
if(i==S||i==T) continue;
dijkstra(S,hot[i]);
if(dis[T]<ans2) ans2=dis[T],ans3=hot[i];
else if(dis[T]==ans2) ans3=min(ans3,hot[i]);
}
if(check) cout<<ans<<" "<<0;
else{
if(ans2==INT_MAX) cout<<"Impossible";
else cout<<ans2<<" "<<ans3;
}
}
赛后写的正解代码o(nlogn):
int n,m,S,T;
int hot[1003];
vector<pair<int,int>> vct[1003];
typedef struct node{
int d,h,id;
bool operator<(const node & x) const{
if(d!=x.d) return d>x.d;
return h>x.h;
}
}node;
int dis[1003],maxh[1003];
bool vis[1003];
priority_queue<node> pq;
void dijkstra(int s){
for(int i=1;i<=n;i++) dis[i]=INT_MAX,maxh[i]=hot[i];
dis[s]=0;
pq.emplace((node){0,0,s});
while(pq.size()){
int from=pq.top().id;
pq.pop();
if(vis[from]) continue;
vis[from]=1;
for(auto v:vct[from]){
int to=v.first,w=v.second;
if(dis[to]>dis[from]+w){
dis[to]=dis[from]+w;
//maxh[to]=max(maxh[to],maxh[from]); 这样取max会wa5分
maxh[to]=max(hot[to],maxh[from]); 这样可以拿满!
因为这个点可能被更新了多次,maxh[to]可能是之前一个更大并且更长的路径更新的,所以不能用maxh[to]取max
pq.emplace((node){dis[to],maxh[to],to});
}
else if(dis[to]==dis[from]+w&&maxh[from]<maxh[to]){
maxh[to]=max(hot[to],maxh[from]); key
pq.emplace((node){dis[to],maxh[to],to});
}
}
}
}
void solve(){
cin>>n>>m>>S>>T;
for(int i=1;i<=n;i++) cin>>hot[i];
for(int i=1;i<=m;i++){
int u,v,w; cin>>u>>v>>w;
vct[u].emplace_back(v,w);
vct[v].emplace_back(u,w);
}
hot[S]=0,hot[T]=0;
dijkstra(S);
if(dis[T]==INT_MAX) cout<<"Impossible";
else cout<<dis[T]<<" "<<maxh[T];
}
RC-u5 贪心消消乐 - 2024 睿抗机器人开发者大赛CAIP-编程技能赛-本科组(国赛) (pintia.cn)
思路:最后一题写的。至关重要的16分!最后十分钟左右交上去拿到的。不知道正解是什么,反正这个暴力模拟得有点小绕,还要模拟下落。我这里下落似乎模拟错了一点点,wa了两分,其他都是T的。模拟下落应该是落到了原本就是黑洞的地方,因为把消除的点也标成了0,应该标成特色数值,和黑洞区分开来,然后再模拟下落,这样应该能拿到没有wa了的两分。
int n;
int maze[103][103];
void solve(){ E 16/30
cin>>n;
for(int i=1;i<=n;i++){
for(int j=1;j<=n;j++){
cin>>maze[i][j];
}
}
int ans=0;
while(1){
int maxn=0;
int x1=0,y1=0,x2=0,y2=0;
for(int i=1;i<=n;i++){
for(int j=1;j<=n;j++){
if(maze[i][j]==0) continue;
for(int g=i;g<=n;g++){
for(int h=j;h<=n;h++){
if(maze[g][h]==0) break;
int sum=0,c=0;
for(int a=i;a<=g;a++){
for(int b=j;b<=h;b++){
if(maze[a][b]==0) c=1;
sum+=maze[a][b];
if(c) break;
}
if(c) break;
}
if(c) break;
if(sum>maxn) x1=i,y1=j,x2=g,y2=h,maxn=sum;
}
}
}
}
if(maxn==0) break;
ans+=maxn;
cout<<'('<<y1<<", "<<x1<<')'<<" "<<'('<<y2<<", "<<x2<<')'<<' '<<maxn<<endl;
for(int i=x1;i<=x2;i++){
for(int j=y1;j<=y2;j++){
maze[i][j]=0;
}
}
for(int i=x1-1;i>=1;i--){
for(int j=y1;j<=y2;j++){
int xx0=i;
if(maze[i][j]!=0){
while(maze[xx0+1][j]==0&&xx0+1<=n) xx0++;
maze[xx0][j]=maze[i][j];
maze[i][j]=0;
}
}
}
}
cout<<ans;
}
总结:这场满分120,拿了102,可以了。