CSP普及赛基础算法练习1

洛谷 P1010 幂次方 -分治算法

https://www.luogu.com.cn/problem/P1010

#include<bits/stdc++.h> 
using namespace std;
void compute(int x){
    if (x==0)    return;    //递归结束条件
    //可以求出2的对数  舍去小数 比如:log2(8)=3 log2(7)
    int t = log2(x); 
    if (t==0){
        cout<<"2(0)";    //2的0次方    
    }
    if (t==1){
        cout<<"2";    //2的1次方
    }
    if (t>1) {//大于2的1次方,递归
        cout<<"2(";
        compute(t);
        cout<<")";//结束递归后添加
    }
    if (pow(2,t)!=x) {//x不等于pow(2,t),说明后面还接着数
        cout<<"+";
        compute(int(x-pow(2,t)));
    }
}
int main(){
    int n;
    cin >> n;
    compute(n);
    return 0;
}

 

洛谷 P1908 逆序对 -分治算法

https://www.luogu.com.cn/problem/P1908

#include<iostream>
using namespace std;
int tmp[500001],nums[500001];
long long sum;
void margeSort(int arr[],int l,int r) {
    if (l>=r)return;
    int mid =l+((r-l)>>1);//找中间点 
    margeSort(arr,l,mid);
    margeSort(arr,mid+1,r);
    int li=l,ri=mid+1,ti=0;
    //每次右边(mid+1~r)放入时说明该数比arr[li]小,
//    所以没放入的左边(li~mid)都比该数大,就添加(mid+1)-li个逆序对即可.
    while (li<=mid && ri<=r) {
        if (arr[li]<=arr[ri]){
            tmp[ti++]=arr[li++];
        }else{
            tmp[ti++]=arr[ri++];
            sum+=(long long)mid+1-li;
        } 
    }
    while (li<=mid){
        tmp[ti++]=arr[li++];
    }
    while (ri<=r){
        tmp[ti++]=arr[ri++];
    }
    for(int i=l;i<=r;i++)arr[i]=tmp[i-l];
}
int main() {
    int n;
    cin >> n;
    for (int i=0;i<n;i++){
        cin>>nums[i];
    }
    margeSort(nums,0,n-1);
    cout<<sum;
    return 0;
}

 

洛谷 P2240 部分背包问题 - 贪心算法

https://www.luogu.com.cn/problem/P2240

#include<bits/stdc++.h>
using namespace std;
struct treasure{
    int weight;
    double price;
    double value;
};
bool cmp(treasure ts1,treasure ts2){
    return ts1.price>ts2.price;
}
int main(){
    int n,t;
    cin>>n>>t;
    treasure ts[n];
    for(int i=0;i<n;i++){
        cin>>ts[i].weight>>ts[i].value;
        ts[i].price=ts[i].value/ts[i].weight;
    }
    sort(ts,ts+n,cmp);
    double ans=0;
    for(int i=0;i<n;i++){
        if(ts[i].weight<=t){
            ans+=ts[i].value;
            t-=ts[i].weight;
        }else{
            ans+=ts[i].price*t;
            break;
        }
    }
    cout<<fixed<<setprecision(2)<<ans;
}

洛谷 P1151 子数整数 - 枚举

https://www.luogu.com.cn/problem/P1151

#include<bits/stdc++.h>
using namespace std;
int main(){
    int k;
    cin>>k;
    bool flag = false;
    for(int i=10000;i<=30000;i++){
        //拆a1a2a3 
        int temp1 = i/100;
        //取a2a3a4 
        // i/10000*10000 保留整万 
        //i-i/10000*10000 去除首位比如:23456变成3456
        //(i-i/10000*10000)/10 --23456变成3456变成345 
        int temp2 =(i-i/10000*10000)/10;
        //取a3a4a5 
        int temp3 = i%1000;
        //判断对应子项是否被k整除 
        if(temp1%k==0 && temp2%k==0 && temp3%k==0){
            cout<<i<<endl;
            flag = true;
        }
    }
    if(!flag){
        cout<<"No";
    }
} 

 

洛谷 P1211 牛式 Prime Cryptarithm - 枚举

https://www.luogu.com.cn/problem/P1211

#include<bits/stdc++.h>
using namespace std;
bool a[10];
//是否给定数字 
bool isValid(int n){
    while(n){
        if(a[n%10]==0){
            return false;
        }
        n/=10;
    }
    return true;
}
int main(){
    int n;
    cin>>n;
    int temp;
    for(int i=0;i<n;i++){
        cin>>temp;
        a[temp]=1;
    }
    int ans=0;
    for(int i=100;i<=999;i++){
        for(int j=10;j<=99;j++){//枚举两个乘数
            int ge= j%10;
            int shi = j/10;
            if(i*ge>999){//第一个数*第二个数个位 
                continue;
            }
            if(i*shi>999){//第一个数*第二个数十位 
                continue;
            }
            if(i*j>9999){//第一个数*第二个数十位 
                continue;
            }
            //i j i*j的个位 i*j的十位 i*j必须都是给定的数字 
            if(isValid(i)&&isValid(j)&&isValid(i*ge)&&isValid(i*shi)&&isValid(i*j)){ 
                    ans++; 
            }
        }
    }
    cout<<ans<<endl;
    return 0;
}

洛谷 P1059 明明的随机数 - 排序

https://www.luogu.com.cn/problem/P1059

#include<bits/stdc++.h>
using namespace std;
int n,a[107],t;
int main(){
    scanf("%d",&n);
    for(int i=0;i<n;i++)
        scanf("%d",&a[i]);
    sort(a,a+n);
    int cnt=1;
    //去重 重复的把前面一个清0 
    for(int i=1;i<n;i++){ 
        if(a[i]==a[i-1]){
            a[i-1]=0;
        }else{
            cnt++;
        }
    }
    printf("%d\n",cnt);
    for(int i=0;i<n;i++){
        if(a[i]>0){
            printf("%d ",a[i]);
        }
    }
    return 0;
}

 

洛谷 P1068 分数线划定 - 排序

https://www.luogu.com.cn/problem/P1068

#include<bits/stdc++.h>
using namespace std;
struct student{
    int no;
    int score;
};
//排序规则 
//分数从大到小 分数相同按学号从小到大 
bool cmp(student st1,student st2){
    if(st1.score!=st2.score)
        return st1.score>st2.score;
    return st1.no<st2.no;
}
student students[5005];
int n,m;
int main(){
    cin>>n>>m;
    for(int i=0;i<n;i++){
        cin>>students[i].no;
        cin>>students[i].score;
    }
    sort(students,students+n,cmp);
    m=m*1.5;//面试人数 向下取整
    //分数线 最后一个录取的人分数 
    int mscore = students[m-1].score;
    int retCnt = m;//记录录取人数
    //计算实际录取人数-最后一个分数多个,相同都录取 
    for(int i=m;i<n;i++){
        if(students[i].score==mscore){
            retCnt++;
        }else{
            break;
        }
    }
    cout<<mscore<<" "<<retCnt<<endl;
    for(int i=0;i<retCnt;i++){
        cout<<students[i].no<<" "<<students[i].score<<endl;
    }
}

 

洛谷 P1093 [NOIP2007 普及组] 奖学金 - 排序

https://www.luogu.com.cn/problem/P1093

#include<bits/stdc++.h>
using namespace std;
 
struct stx{
    int yw,sx,yy;//yw 语文成绩,sx数学成绩, yy英语成绩 
    int sum,no;//总分,学号 
}score[501]; 

//排序规则
//按总分从大到小
//总分相同按语文从大到小
//总分和语文相同 按学号从小到大 
int cmp(stx x1,stx x2){
    if(x1.sum!=x2.sum) return x1.sum>x2.sum;
    if(x1.yw!=x2.yw) return x1.yw>x2.yw;
    return x1.no<x2.no;
}
 
int main(){
    int n;
    cin>>n;
    //读取数据到数据结构体 
    for(int i=1;i<=n;i++){
        cin>>score[i].yw>>score[i].sx>>score[i].yy;
        score[i].sum=score[i].yw+score[i].sx+score[i].yy;
        score[i].no=i;
    }
    //sort从第一个开始的n个人排序 
    sort(score+1,score+n+1,cmp);
    //取前5人 
    for(int i=1;i<=5;i++){
        cout<<score[i].no<<" "<<score[i].sum<<endl; 
    }
}

 

posted @ 2021-05-23 10:18  new-code  阅读(166)  评论(0)    收藏  举报