CCF計算機能力認證2019-03題解

01 小中大

在這裏插入圖片描述

思路

前兩道題一般都非常水,注意一些細節就很容易ac,這道題就按照題意來就好了,要注意的一個地方就是輸出格式,這道題卡輸出格式卡的特別嚴格,尤其是中位數的格式,要注意分中位數爲整數和分數進行輸出,不然就會wa

#include<iostream>
#include<algorithm>
using namespace std;
const int maxn=100001;
int n,mid,a[maxn];
int main()
{
    cin>>n;
    for(int i=0; i<n; i++)
        cin>>a[i];
    sort(a,a+n);
    if(n%2==0)
    {
        mid=a[n/2]+a[n/2+1];
        if(mid%2!=0)
            cout<<a[n]<<" "<<mid/2<<".5"<<" "<<a[1];
        else
            cout<<a[n]<<" "<<mid/2<<" "<<a[1];
    }
    else
    {
        mid=a[n/2+1];
        cout<<a[n]<<" "<<mid<<" "<<a[1];
    }
    return 0;
}

02 24點

在這裏插入圖片描述

思路

也是非常基礎的一道題,直接將數據存入棧中,然後遇到乘除的時候先計算出結果,然後將結果放入棧中,注意將減法轉化爲加法。

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cmath>
#include<map>
#include<ctime>
#include<vector>
#include<cstring>
#include<iomanip>
#include<stack>
using namespace std;
int main()
{
    int T;
    cin>>T;
    string s;
    stack<int> num1,num2;
    while(T--)
    {
        cin>>s;
        bool flag=false;
        for(int i=0; i<s.size(); i++)
        {
            if(s[i]=='-')
                flag=true;
            else if(s[i]=='x'||s[i]=='/')
            {
                int a=num1.top();
                num1.pop();
                if(s[i]=='x')
                    a*=(s[i+1]-'0');
                else
                    a/=(s[i+1]-'0');
                num1.push(a);
                i++;
            }
            else if(s[i]!='+')
            {
                int a;
                a=s[i]-'0';
                if(flag)
                {
                    a=-a;
                    flag=false;
                }
                num1.push(a);
            }
        }
        int ans=0;
        while(!num1.empty())
        {
            ans+=num1.top();
            num1.pop();

        }
        if(ans==24)
            cout<<"Yes\n";
        else
            cout<<"No\n";
    }
}


03 損壞的RAID5

在這裏插入圖片描述
在這裏插入圖片描述
在這裏插入圖片描述
在這裏插入圖片描述

思路

一道究極惡心的模擬題,關鍵就是看懂題意,然後按題意模擬就好了,算法方面沒有難度,但就是噁心人,我都懷疑這是在考語文的閱讀理解,真的不想做這道題了,還要注意一點,直接寫cin的話會TL,但是因爲用到了string,所以scanf又不能用,所以需要在開頭加一句ios::sync_with_stdio(false);防止cin超時。


#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
string book="0123456789ABCDEF";
int n,m,s,l,_maxk;
int id;
string a[10005];
int _toint(char ch)
{
    if(ch>='0'&&ch<='9')
        return(ch-'0');
    else
        return(ch-'A'+10);
}
void _xor(string &s1,string s2)
{
    for(int i=0; i<s2.size(); i++)
    {
        int x=_toint(s1[i]);
        int y=_toint(s2[i]);
        s1[i]=book[(x^y)];
    }
}
string result(int disk,int start)
{
    string s1(8,'0');
    for(int i=0; i<n; i++)
    {
        if(i!=disk)
            _xor(s1,a[i].substr(start,8));
    }
    return s1;
}
int main()
{
    ios::sync_with_stdio(false);//避免c++中cin操作超時。
    cin>>n>>s>>l;
    //s爲陣列條帶大小,單位爲塊
    //2個字符等於一個字節,一個塊爲4個字節,8個字符
    for(int i=0; i<l; i++)
    {
        cin>>id;
        cin>>a[id];
        _maxk=a[id].size()/8/s;//最大的條帶數目
    }
    cin>>m;
    while(m--)
    {
        int b;
        cin>>b;//要讀取的塊的編號
        int y=b/s;//y是條帶號
        int k=y/(n-1);//k是條帶在第k排
        int k1=(y%(n*n-n))/(n-1);//k1是數據帶在第k1排
        int rd1=(n-1)-k1%n;//rd1是冗餘帶所在的磁盤編號
        int diskid=(y%(n*n-n)+1-k1*(n-1)+rd1)%n;//diskid是數據帶所在的磁盤編號
        if(k>=_maxk)
            cout<<"-"<<endl;
        else if(a[diskid].size()!=0)
            cout<<a[diskid].substr(8*(b%s+k1*s),8)<<endl;
        else if(a[diskid].size()==0&&(l==n-1))
            cout<<result(diskid,8*(b%s+k1*s))<<endl;
        else
            cout<<"-"<<endl;
    }
    return 0;
}

04 消息傳遞接口

額,不會,疊甲,過!
(os:這套題好惡心啊,基本上難點都在讀題,然後讀懂模擬就好了,算法強,但是讀題弱的孩子好可憐)

05 317號子任務

在這裏插入圖片描述
在這裏插入圖片描述

#include <bits/stdc++.h>
using namespace std;
struct E
{
    int v,w;
    bool operator < (const E&b)const
    {
        return w>b.w;
    }
};
int n,m,k;
int ff[10000+10];
priority_queue<int,vector<int>,greater<int> > d[10000];
vector<E> edge[10000];
 
 
void dijkstra(int k)
{
    priority_queue<E> Q;
    int dis[10000];
    for(int i=0;i<n;i++)
        dis[i]=0x3f3f3f3f;
    dis[k]=0;
    Q.push((E){k,0});
    while(!Q.empty())
    {
        E t=Q.top();
        Q.pop();
        if (t.w!=dis[t.v]) continue;
        d[t.v].push(t.w);
        int m=edge[t.v].size();
        int u,w;
        for (int i=0;i<m;i++)
        {
            u=edge[t.v][i].v;
            w=edge[t.v][i].w;
            if (dis[u]>dis[t.v]+w)
                dis[u]=dis[t.v]+w,
                Q.push((E){u,dis[u]});
        }
    }
}
 
int main()
{
    scanf("%d%d%d",&n,&m,&k);
    int num=0,x;
    for(int i=0;i<n;i++)
    {
        scanf("%d",&x);
        if(x)ff[num++]=i;
    }
    int u,v,w;
    for(int i=0;i<m;i++)
    {
        scanf("%d%d%d",&u,&v,&w);
        u--;v--;
        edge[u].push_back((E){v,w});
        edge[v].push_back((E){u,w});
    }
    for(int i=0;i<num;i++)
        dijkstra(ff[i]);
    long long ans;
 
 
    for(int i=0;i<n;i++)
    {
        int cnt=k;
        ans=0;
        while(!d[i].empty()&&cnt--)
        {
            ans+=d[i].top();
            d[i].pop();
        }
        printf("%lld\n",ans);
    }
 
    return 0;
}
 

思路

圖論中的最短路徑,使用dj會超時,這裏用優先隊列優化後還是超時,但是60分了,我太難了

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章