首页 > 其他分享 >PAT乙级题解

PAT乙级题解

时间:2023-02-04 14:46:18浏览次数:57  
标签:知识点 cnt PAT int 题解 代码 namespace 乙级 include

1001 害死人不偿命的(3n+1)猜想

传送门
知识点:简单模拟
思路:判断奇偶,根据题意即可
参考代码

点击查看代码
#include<iostream>
using namespace std;

int main()
{
    int n,cnt=0;
    cin>>n;
    while(n!=1){
        if(n%2)//奇数
            n=(3*n+1);
        n/=2;
        cnt++;
    }
    cout<<cnt<<endl;
    return 0;
}

1002 写出这个数

传送门
知识点:模拟,递归,映射
思路
输入数据过大,无法用int或long long存储,只能用string;
遍历string,ch-'0'即可得到该位数字,将各位数字相加得到sum,100位数字相加数据小于1000,使用int存储;
将sum拆分为数组,然后遍历输出映射的拼音,数字与拼音的映射使用string数组即可。
参考代码

点击查看代码
#include<iostream>
using namespace std;

string num[10]={"ling","yi","er","san","si","wu","liu","qi","ba","jiu"};
int cnt=0;
int a[110];

//将数x拆分为数组,递归
void fun(int x){
    if(x>=10)   fun(x/10);
    a[cnt++]=x%10;
}
int main()
{
    string st;
    int sum=0;
    cin>>st;
    //各位数字相加
    for(char ch:st)
        sum+=(ch-'0');
    fun(sum);
    //按位输出各数字映射的拼音
    for(int i=0;i<cnt;i++){
        cout<<num[a[i]];
        if(i!=cnt-1)    cout<<" ";
    }
    cout<<endl;
    return 0;
}

1003 我要通过!

传送么
知识点:模拟,找规律
思路
根据题意可以得出;
1、不含有PAT以外的字符;
2、P、T有且仅有一个;
3、字符串的格式为xPA..ATx..x,PT之间的A个数与T后面x的个数相等,而x也是由A组成的字符串,以cnt0、cnt1、cnt2表示其中A的个数,cnt0*cnt1==cnt2;
4、PT之间至少有一个A
参考代码

点击查看代码
#include<iostream>
using namespace std;

int main()
{
    int n;
    cin>>n;
    while(n--){
        string st;
        cin>>st;
        bool flag=true;
        int cnt=0;
        int cnt0=0,cnt1=0,cnt2=0;
        int cntp=0,cntt=0;
        for(char ch:st){
            if(ch=='P'){
                //记录P之前的A
                cnt0=cnt;
                cnt=0;
                cntp++;
            }
            else if(ch=='A')
                cnt++;
            else if(ch=='T'){
                //记录PT之间的A
                cnt1=cnt;
                cnt=0;
                cntt++;
            }
            //不能含有PAT以外的字符
            else    flag=false;
        }
        //记录T之后的A
        cnt2=cnt;
        //P、T有且仅有一个
        if(cntp!=1||cntt!=1)    flag=false;
        //PT之间至少有一个A,xPA..ATx..x
        if(cnt1==0||cnt1*cnt0!=cnt2) flag=false;
        if(flag==true)    cout<<"YES";
        else    cout<<"NO";
        if(n!=0)    cout<<endl;
    }
    return 0;
}

1004 成绩排名

传送门
知识点:结构体,排序
思路:使用结构体存储数据,使用sort以成绩为基准来排序,输出最高和最低成绩
参考代码

点击查看代码
#include<iostream>
#include<algorithm>
using namespace std;

//使用结构体存储数据
struct STU{
    int sorce;
    string num;
    string name;
};
STU stu[110];

bool cmp(STU A,STU B){
    return A.sorce<B.sorce;
}
int main()
{
    int n;
    cin>>n;
    for(int i=0;i<n;i++){
        cin>>stu[i].name>>stu[i].num>>stu[i].sorce;
    }
    //使用sort以成绩为基准来排序
    sort(stu,stu+n,cmp);
    //输出最高和最低成绩
    cout<<stu[n-1].name<<" "<<stu[n-1].num<<endl;
    cout<<stu[0].name<<" "<<stu[0].num<<endl;
    return 0;
}

1005 继续(3n+1)猜想

传送门
知识点:模拟,排序
思路:每个数x,经过一步步计算到达1,途中标记每一个中间量,表示他们被遍历过,可以由前面的数推算得到;剩下没有被标记过的就是关键数,从大到小排序后输出
参考代码

点击查看代码
#include<iostream>
#include<algorithm>
using namespace std;

int a[110],b[110];
bool v[110];

//从大到小排序
bool cmp(int a,int b){
    return a>b;
}
int main()
{
    int n;
    cin>>n;
    for(int i=0;i<n;i++){
        cin>>a[i];
        int x=a[i];
        while(x!=1){
            if(x%2) x=(3*x+1);
            x/=2;
            //数据范围为1~100
            if(x>100)   continue;
            //标记数字x被遍历
            v[x]=true;
        }
    }
    //将关键数存到到另一个数组,方便排序
    int cnt=0;
    for(int i=0;i<n;i++)
        if(v[a[i]]==false)
            b[cnt++]=a[i];
    sort(b,b+cnt,cmp);
    cout<<b[0];
    for(int i=1;i<cnt;i++)
        cout<<" "<<b[i];
    cout<<endl;
    return 0;
}

1006 换个格式输出整数

传送门
知识点:简单模拟
思路:分离百十个位上的数,按照题意输出
参考代码

点击查看代码
#include<iostream>
using namespace std;

int main()
{
    int n;
    cin>>n;
    //分离百十个上的数
    int b=n/100,s=(n/10)%10,g=n%10;
    for(int i=0;i<b;i++)
        cout<<"B";
    for(int i=0;i<s;i++)
        cout<<"S";
    for(int i=1;i<=g;i++)
        cout<<i;
    cout<<endl;
    return 0;
}

1007 素数对猜想

传送门
知识点:模拟
思路:遍历所有差为2的数对,判断两个数是否都是素数
参考代码

点击查看代码
#include<iostream>
using namespace std;

//判断素数
bool check(int x){
    for(int i=2;i*i<=x;i++)
        if(x%i==0)
            return false;
    return true;
}
int main()
{
    int n,cnt=0;
    cin>>n;
    for(int i=3;i<=n-2;i++)
        if(check(i)&&check(i+2))
            cnt++;
    cout<<cnt<<endl;
    return 0;
}

1008 数组元素循环右移问题

传送门
知识点:数组
思路:将数组整体翻转,再将前半和后半数组分别翻转,可以达到右移效果
参考代码

点击查看代码
#include<iostream>
#include<vector>
#include<algorithm>
using namespace std;

int main()
{
    int n,m;
    cin>>n>>m;
    //移动所有数字相当没动
    m=m%n;
    vector<int> a(n);
    for(int i=0;i<n;i++)
        cin>>a[i];
    reverse(a.begin(),a.end());
    reverse(a.begin(),a.begin()+m);
    reverse(a.begin()+m,a.end());
    cout<<a[0];
    for(int i=1;i<n;i++)
        cout<<" "<<a[i];
    cout<<endl;
    return 0;
}

1009 说反话

传送门
知识点:字符串
思路:使用string数组存储数据,reverse将数组翻转
参考代码

点击查看代码
#include<iostream>
#include<vector>
#include<algorithm>
#include<cstring>
using namespace std;

int main()
{
    vector<string> words;
    string w;
    while(cin>>w)
        words.push_back(w);
    reverse(words.begin(),words.end());
    cout<<words[0];
    for(int i=1;i<words.size();i++)
        cout<<" "<<words[i];
    cout<<endl;
    return 0;
}

1010 一元多项式求导

传送门
知识点:模拟
思路:根据题意求导就行,注意零多项式
参考代码

点击查看代码
#include<iostream>
using namespace std;

int main()
{
    int m,n;
    cin>>m>>n;
    //特判零多项式
    if(n==0){
        puts("0 0");
        return 0;
    }
    if(m*n!=0)
        cout<<m*n<<" "<<n-1;
    while(cin>>m>>n){
        if(m*n!=0)
            cout<<" "<<m*n<<" "<<n-1;
    }
    return 0;
}

1011 A+B 和 C

传送门
知识点:数据范围
思路:int取值范围:-231~231-1;long long取值范围:-263~263-1
参考代码

点击查看代码
#include<iostream>
using namespace std;

int main()
{
    int T;
    cin>>T;
    for(int i=1;i<=T;i++){
        cout<<"Case #"<<i<<": ";
        long long a,b,c;
        cin>>a>>b>>c;
        if(a+b>c)
            puts("true");
        else    puts("false");
    }
    return 0;
}

1012 数字分类

传送门
知识点:模拟
思路:不难发现,将数字对5取模就得到了分类,使用switch-case语句来更清楚的表达多分支;由于A4为小数,需要特判
关键信息:若分类之后某一类不存在数字,则在相应位置输出 N。
参考代码

点击查看代码
#include<iostream>
#include<iomanip>
using namespace std;

int main()
{
    int n;
    cin>>n;
    int a[6]={0},cnt=0;
    bool flag=true,flag2=false;//表示加,表示A2这组没有数字
    for(int i=0;i<n;i++){
        int x;
        cin>>x;
        switch(x%5){
            case 0:
                if(x%2==0)  a[1]+=x;
                break;
            case 1:
                flag2=true;
                a[2]+=(flag?x:-x);
                flag=!flag;
                break;
            case 2:
                a[3]++;
                break;
            case 3:
                cnt++;
                a[4]+=x;
                break;
            case 4:
                a[5]=max(a[5],x);
                break;
        }
    }
    cout<<fixed<<setprecision(1);
    for(int i=1;i<=5;i++){
        int t=a[i];
        //A2的运算中有加有减,所以最终结果为0不能表示这类没有数字
        if((i!=2&&t==0)||(i==2&&flag2==false))
            cout<<"N";
        else{
            if(i==4)
                cout<<double(t)/cnt;
            else    cout<<t;
        }
        if(i!=5)    cout<<" ";
    }
    return 0;
}

1013 数素数

传送门
知识点:数学知识-素数
思路:先求出足够多的素数,然后输出;
参考代码

点击查看代码
#include<iostream>
#include<vector>
using namespace std;

bool check(int x){
    for(int i=2;i*i<=x;i++)
        if(x%i==0)
            return false;
    return true;
}
int main()
{
    vector<int> a;
    a.push_back(0);//让数组从1开始存储
    for(int i=2;i<2e5;i++)
        if(check(i))
            a.push_back(i);
    int m,n;
    cin>>m>>n;
    for(int i=m;i<=n;i++){
        cout<<a[i];
        if((i-m)%10==9)
            cout<<endl;
        else if(i!=n)   cout<<" ";
    }
    return 0;
}

1014 福尔摩斯的约会

传送门
知识点:模拟
思路
第一个条件:第一对相同的大写英文字母,以大写字母来代指星期,那么只有'A'~'G'是有效的
第二个条件:第一对相同的字符,24小时以'0''9'和'A''N'来代指
第三个条件:第一对相同英文字母,不区分大小写
参考代码

点击查看代码
#include<iostream>
using namespace std;

string d[7]={"MON","TUE","WED","THU","FRI","SAT","SUN"};

bool check0(char ch){//判断是否为大写字母
    return ch>='A'&&ch<='Z';
}
bool check1(char ch){//判断是否为数字
    return ch>='0'&&ch<='9';
}
bool check2(char ch){//判断是否为小写字母
    return ch>='a'&&ch<='z';
}
int main()
{
    string s0,s1,t0,t1;
    cin>>s0>>s1>>t0>>t1;
    bool flag=false;
    for(int i=0;i<s0.size()&&i<s1.size();i++){
        //第二个条件:第一对相同的字符
        if(flag&&s0[i]==s1[i]){
            if(check1(s0[i])){
                cout<<"0"<<s0[i]-'0'<<":";
                break;
            }
            else if(s0[i]>='A'&&s0[i]<='N'){
                cout<<s0[i]-'A'+10<<":";
                break;
            }
        }
        //第一个条件:第一对相同的大写英文字母
        if(s0[i]==s1[i]&&s0[i]>='A'&&s0[i]<='G'){
            cout<<d[s0[i]-'A']<<" ";
            flag=true;//表示开始判断第二对
        }
    }
    //第三个条件:第一对相同英文字母
    for(int i=0;i<t0.size()&&i<t1.size();i++){
        if(t0[i]==t1[i]&&(check0(t0[i])||check2(t1[i]))){
            if(i<10)
                cout<<"0"<<i;
            else    cout<<i;
            break;
        }
    }
    return 0;
}

1015 德才论

传送门
知识点:结构体排序
思路:根据题意来划分组;编写cmp函数用于排序,先以组别然后德分最后准考证据
参考代码

点击查看代码
#include<iostream>
#include<algorithm>
#include<vector>
using namespace std;

struct STU{
    string num;//学号
    int x,y;//德分,才分
    int score;//总分
    int group;//组别
};
vector<STU> stu;

bool cmp(STU a,STU b){
    if(a.group!=b.group)
        return a.group<b.group;
    else if(a.score!=b.score)
        return a.score>b.score;
    else if(a.x!=b.x)
        return a.x>b.x;
    return a.num<b.num;
}
int main()
{
    int n,l,h;
    cin>>n>>l>>h;
    for(int i=0;i<n;i++){
        STU t;
        int g;
        cin>>t.num>>t.x>>t.y;
        if(t.x<l||t.y<l)    continue;
        if(t.x>=h&&t.y>=h)  g=1;
        else if(t.x>=h) g=2;
        else if(t.x>=t.y)   g=3;
        else    g=4;
        t.group=g;
        t.score=t.x+t.y;
        stu.push_back(t);
    }
    sort(stu.begin(),stu.end(),cmp);
    cout<<stu.size()<<endl;
    for(int i=0;i<stu.size();i++)
        cout<<stu[i].num<<" "<<stu[i].x<<" "<<stu[i].y<<endl;
    return 0;
}

1016 部分A+B

传送门
知识点:模拟
思路:遍历每一位数,记录目标数D出现次数cnt,根据目标数D和出现次数cnt构造P
参考代码

点击查看代码
#include<iostream>
using namespace std;

//记录d在x中的出现次数
int fun(int x,int d){
    int cnt=0;
    while(x>1){
        if(d==x%10) cnt++;
        x/=10;
    }
    return cnt;
}
//构造cnt位的x
int p(int x,int cnt){
    int ans=0;
    for(int i=0;i<cnt;i++)
        ans=ans*10+x;
    return ans;
}
int main()
{
    int a,da,b,db;
    cin>>a>>da>>b>>db;
    cout<<p(da,fun(a,da))+p(db,fun(b,db));
    return 0;
}

1017 A除以B

传送门
知识点:高精度
思路:高精度除法的模板题
参考代码

点击查看代码
#include<iostream>
#include<vector>
#include<algorithm>
using namespace std;

vector<int> dev(vector<int> &A,int b,int &r){
    vector<int> C;
    for(int i=A.size()-1;i>=0;i--){
        r=r*10+A[i];
        C.push_back(r/b);
        r%=b;
    }
    //去除前导0
    reverse(C.begin(),C.end());
    while(C.size()>1&&C.back()==0)  C.pop_back();
    return C;
}
int main()
{
    string a;
    int b;
    vector<int> A;
    cin>>a>>b;
    //逆序输入、逆序输出,和其他高精度运算保持一致
    for(int i=a.size()-1;i>=0;i--)
        A.push_back(a[i]-'0');
    //余数
    int r=0;
    vector<int> q=dev(A,b,r);
    for(int i=q.size()-1;i>=0;i--)  cout<<q[i];
    cout<<" "<<r;
    return 0;
}

1018 锤子剪刀布

传送门
知识点:映射,模拟
思路:将字符和数字做映射,‘BCJ’映射为‘012’;平局两字符相等,相减为0;甲胜的情况BC、CJ、JB相减为-1、-1、2,加3模3后都为2;甲负即乙胜的情况为两字符相减后加3模3为1;在判断胜负的过程中记录每种字符胜利的次数
参考代码

点击查看代码
#include<iostream>
#include<map>
using namespace std;

map<char,int> h={{'B',0},{'C',1},{'J',2}};
char s[3]={'B','C','J'};
int j[3];//甲的胜、负、平
int x[3],y[3];//布,锤子,剪刀

int main()
{
    int n;
    cin>>n;
    for(int i=0;i<n;i++){
        char ch0,ch1;
        cin>>ch0>>ch1;
        int flag=(h[ch0]-h[ch1]+3)%3;
        j[flag]++;
        if(flag==2)//甲胜
            x[h[ch0]]++;
        else if(flag==1)//乙胜
            y[h[ch1]]++;
    }
    cout<<j[2]<<" "<<j[0]<<" "<<j[1]<<endl;
    cout<<j[1]<<" "<<j[0]<<" "<<j[2]<<endl;
    char J='B',Y='B';
    int num0=x[0],num1=y[0];
    for(int i=1;i<=2;i++)
        if(num0<x[i]){
            num0=x[i];
            J=s[i];
        }
    for(int i=1;i<=2;i++)
        if(num1<y[i]){
            num1=y[i];
            Y=s[i];
        }
    cout<<J<<" "<<Y;
    return 0;
}

1019 数字黑洞

传送门
知识点:模拟
思路
将输入的数字拆分为数组,排一次升序一次降序,再转化为数字,作相减操作,差作为下次循环的输入数字;
判断循环结束条件为差为0或者6174,当升序降序得到的数字相同时差为0,也意味着原来的数字各位相同;
注意不可以在开头判断输入为6174,因为当输入为6174时也应该走一遍这个过程即7641 - 1467 = 6174
参考代码

点击查看代码
#include<iostream>
#include<algorithm>
#include<vector>
using namespace std;

//将数字转化为数组
vector<int> fun0(int n){
    vector<int> a;
    while(n>0){
        a.push_back(n%10);
        n/=10;
    }
    //加前导0
    if(a.size()<4){
        while(a.size()<4)
            a.push_back(0);
    }
    reverse(a.begin(),a.end());
    return a;
}
//将数组转化为数字
int fun1(vector<int> a){
    int res=0;
    for(int num:a)
        res=res*10+num;
    return res;
}
bool cmp(int a,int b){
    return a>b;
}
int main()
{
    int n;
    cin>>n;
    while(true){
        vector<int> x=fun0(n);
        sort(x.begin(),x.end(),cmp);
        int a=fun1(x);
        reverse(x.begin(),x.end());
        int b=fun1(x);
        n=a-b;
        printf("%04d - %04d = %04d\n",a,b,n);
        if(n==0||n==6174)   break;
    }
    return 0;
}

1020 月饼

传送门
知识点:结构体排序,贪心
思路:要想获取最大收益,那么在需求量固定的情况下,应该尽可能卖更贵即单价更高的;输入为总量和总价,算出单价,根据单价排降序
参考代码

点击查看代码
#include<iostream>
#include<algorithm>
using namespace std;

struct CAKE{
    double stock,sell,unit;
};
CAKE cake[1010];

bool cmp(CAKE a,CAKE b){
    return a.unit>b.unit;
}
int main()
{
    int n,m;
    cin>>n>>m;
    for(int i=0;i<n;i++)
        cin>>cake[i].stock;
    for(int i=0;i<n;i++){
        cin>>cake[i].sell;
        cake[i].unit=cake[i].sell/cake[i].stock;
    }
    //贪心法,按照单价来排序,优先选最贵的
    sort(cake,cake+n,cmp);
    double ans=0;
    for(int i=0;i<n;i++)
        if(m>=cake[i].stock){
            ans+=cake[i].sell;
            m-=cake[i].stock;
        }
        else{
            ans+=(m*cake[i].unit);
            break;
        }
    printf("%.2f\n",ans);
    return 0;
}

标签:知识点,cnt,PAT,int,题解,代码,namespace,乙级,include
From: https://www.cnblogs.com/cmml/p/17079785.html

相关文章

  • 题解 G. Grammar Path 2020-2021 ICPC NERC (NEERC), North-Western Russia Regional
    传送门【大意】给定一个CNF和一个有向图。有向图上的每一条边都写上了一个字母。要求你从\(s\)到\(t\)走一条尽可能短的路,且将经过的字母写下来后,这个字符串能被......
  • java中PATH和CLASSPATH
    1、windows中临时设置PATH的方法(只在当前窗口中有效)F:\ch01>D:\Java\jdk-11.0.7\bin\javacF:\ch01>setpath=D:\Java\jdk-11.0.7\bin\F:\ch01>javacWelcome.javaF:\ch......
  • [JOI 2021 Final] 地牢 3 题解
    做法学习自日语酱的题解/hs/bx。本文旨在讲述我个人看完题解对此题做法的理解,可以视作对日语酱题解的注解(?。本人很菜,很可能出错,请谅解qwq。首先,对样例进行模拟,得到......
  • 最小公倍佩尔数 题解
    首先需要知道\(f\)是个啥这里直接给出结论,过程可以看大佬的博客\(f(n)=2f(n-1)+f(n-2)\)\(f(0)=0\)\(f(1)=1\)这种类似斐波那契数列的递推式有结论\(gcd(......
  • P3119 [USACO15JAN]Grass Cownoisseur G 题解
    做过的原题,模拟赛时PDF里的题面实在有点难受。首先有显然结论:在一个环上反走一定是不值的,因为环上的点本来就相互可达。所以考虑缩点。缩点后的问题可以看成:求对于每一......
  • P8368 [LNOI2022] 串 题解
    题目链接题目分析题目要求我们构造一个最长的\(T\)序列,我们首先从每个\(T_i\)入手,思考如何安排才能合法。容易观察到对于每个\(T_i\),合法的\(T_{i-1}\)有两种方......
  • 【题解】P5219 无聊的水题 I
    思路prufer序列+卷积优化dp.首先考虑到令\(a\)为原树的prufer序列,则\(\sum\limits_{i=1}^{n-2}[a_i=k]=\operatorname{deg}(k)\),其中\(\operatorname......
  • IIS WordPress 单站点,多站点 中文URL乱码和重定向多次问题解决方法
    前提是需要安装IISURL重写组件(安装方法这里不说明,搜一下资料就有)1、站点网站根目录新增一个chineseurl.php文件用来处理中文url问题<?php//IISMod-Rewriteif(is......
  • Maven Use STAR or POSIX extensions to overcome this limit 报错问题解决
     问题:Mavenassembly-plugin在打包的时候如果出现groupid'707420648'istoobig(>2097151). UseSTARorPOSIXextensionstoovercomethislimit解决:只需在......
  • vue嵌套路由子路由 path 注意
    子路由的地址如果是希望拼接父路由地址,子路由的path仅写名称,不写“/”,如果希望是另外的地址,则直接以“/”开头。{path:"/lifetools",name:"li......