2019-3-31義烏中學比賽題解

比賽

題目仍是比較簡單的,T3 T4都沒要求輸出步驟ios

T1 [CF6C]Alice, Bob and Chocolate

題目傳送門c++

一開始看到這題總想寫個多線程,但確定是行不通的。(比賽時還寫得十分複雜,不過居然能夠過誒)不能同時執行兩我的,那麼就交替着執行。算法

注意:處理好兩我的在吃同一塊巧克力的狀況數組

看代碼吧:多線程

#include<bits/stdc++.h>
using namespace std;
const int N=100000+10;
int t[N];
int n,cnta,cntb;
inline int read()
{
    int tot=0;
    char c=getchar();
    while(c<'0'||c>'9')
    {
        c=getchar();
    }
    while(c>='0'&&c<='9')
    {
        tot=(tot<<1)+(tot<<3)+c-'0';
        c=getchar();
    }
    return tot;
}
int main()
{
    n=read();
    for(int i=1;i<=n;i++)
    {
        t[i]=read();
    }
    int pa=1,pb=n;
    while(pa<=pb)
    {
        //cout<<pa<<" "<<pb<<" "<<cnta<<" "<<cntb<<endl;
        if(cnta<=cntb)cnta+=t[pa++];
        else cntb+=t[pb--];
        //system("pause");
    }
    //cout<<cnta<<" "<<cntb<<endl;
    cout<<pa-1<<" "<<n-pb<<endl;//輸出需處理好
    return 0;
}

T2 [CF910C] Minimum Sum

題目傳送門ui

當時看到這題一臉懵逼,莫名想到了複雜度爲O(10000000000*n)的算法,然而確定會超時(廢話)spa

接着想到了貪心。線程

很明顯這題是要用每一個字母的權值進行排序。而後依次進行賦值。code

注意:不能有前導零,因此要進行特判排序

看代碼吧:

#include<bits/stdc++.h>
using namespace std;
string s[1100];
int n;
struct Node
{
    int num,sum;
    bool first;
}word[11];
int p[11];
bool vis[11];
inline bool cmp(Node u,Node v)
{
    return u.sum>v.sum;
}
int main()
{
    ios::sync_with_stdio(false);
    cin>>n;
    for(int i=1;i<=10;i++)word[i].num=i;
    for(int i=1;i<=n;i++)
    {
        cin>>s[i];
        word[s[i][0]-'a'+1].first=1;
        for(int j=0;j<s[i].size();j++)
        {
            word[s[i][j]-'a'+1].sum+=pow(10,s[i].size()-j);
        }
    }
    sort(word+1,word+11,cmp);
    /*for(int i=1;i<=10;i++)
    {
        cout<<word[i].num<<" "<<word[i].sum<<" "<<word[i].first<<endl;
    }*/
    for(int i=1;i<=10;i++)
    {
        if(word[i].first)
        {
            for(int j=1;j<=9;j++)if(!vis[j])
            {
                vis[j]=1;
                p[word[i].num]=j;
                break;
            }
        }
        else
        {
            for(int j=0;j<=9;j++)if(!vis[j])
            {
                vis[j]=1;
                p[word[i].num]=j;
                break;
            }
        }
    }
    /*for(int i=1;i<=10;i++)cout<<p[i]<<" ";
    cout<<endl;*/
    int ans=0;
    for(int i=1;i<=n;i++)
    {
        int cnt=0;
        for(int j=0;j<s[i].size();j++)
        {
            cnt=cnt*10+p[s[i][j]-'a'+1];
        }
        ans+=cnt;
    }
    cout<<ans<<endl;
    return 0;
}

T3 [CF2B]The least round way

題目傳送門

看到這題,在比賽時寫的是一種特別奇怪的作法,開了兩個數組進行DP,一個存0的個數,另外一個存去掉後面的0的數。

最終只剩10分TAT

老師講:

要把數分解成2和5,由於只有2*5纔會出現10,數的後面纔會出現0.

注意:一但出現0,程序就會出錯,because 0*XXX=0

看代碼吧:

#include<bits/stdc++.h>
using namespace std;
const int N=1010;
const int INF=0x3f3f3f3f;
int two[N][N];
int five[N][N];
int Map[N][N];
int dp1[N][N],dp2[N][N];
int n;
inline int read()
{
    int tot=0;
    char c=getchar();
    while(c<'0'||c>'9')
    {
        c=getchar();
    }
    while(c>='0'&&c<='9')
    {
        tot=(tot<<1)+(tot<<3)+c-'0';
        c=getchar();
    }
    return tot;
}
inline int get(int num,int c)
{
    int cnt=0;
    while(num%c==0&&num!=0)
    {
        num/=c;
        cnt++;
    }
    return cnt;
}
int main()
{
    n=read();
    for(int i=1;i<=n;i++)
    {
        for(int j=1;j<=n;j++)
        {
            Map[i][j]=read();
            if(Map[i][j]==0)
            {
                cout<<1<<endl;
                return 0;
            }
            two[i][j]=get(Map[i][j],2);
            five[i][j]=get(Map[i][j],5);
        }
    }
    for(int i=2;i<=n;i++)dp1[i][0]=dp1[0][i]=dp2[i][0]=dp2[0][i]=INF;
    /*for(int i=1;i<=n;i++)
    {
        for(int j=1;j<=n;j++)cout<<two[i][j]<<" ";
        cout<<endl;
    }cout<<endl;
    for(int i=1;i<=n;i++)
    {
        for(int j=1;j<=n;j++)cout<<five[i][j]<<" ";
        cout<<endl;
    }cout<<endl;*/
    for(int i=1;i<=n;i++)
    {
        for(int j=1;j<=n;j++)
        {
            dp1[i][j]=min(dp1[i-1][j],dp1[i][j-1])+two[i][j];
            dp2[i][j]=min(dp2[i-1][j],dp2[i][j-1])+five[i][j];
        }
    }
    /*for(int i=1;i<=n;i++)
    {
        for(int j=1;j<=n;j++)cout<<dp1[i][j]<<" ";
        cout<<endl;
    }cout<<endl;
    for(int i=1;i<=n;i++)
    {
        for(int j=1;j<=n;j++)cout<<dp2[i][j]<<" ";
        cout<<endl;
    }cout<<endl;*/
    cout<<min(dp1[n][n],dp2[n][n])<<endl;
    return 0;
}

T4 [CF41D]Pawn

題目傳送門

看到這題,二話不說先寫爆搜,寫完後發現30*30的數據就足以卡爆個人醜陋的代碼了。

因而很慌......

最後想到了:這不就是那個叫什麼...什麼數字三角形嘛...只不過那個...這個就是方的...方的而已呀,最終寫了個DP。

看代碼吧:

#include<bits/stdc++.h>
using namespace std;
int n,m,k;
int Map[110][110];
int ans=-1;
bool dp[110][110][910];
/*inline void DFS(int x,int y,int cnt)
{
    if(x<1||y<1||x>n||y>m)return;
    //cout<<x<<" "<<y<<" "<<cnt<<endl;
    if(x==n)
    {
        if((cnt+Map[x][y])%(k+1)==0)ans=max(ans,cnt+Map[x][y]);
        return;
    }
    DFS(x+1,y+1,cnt+Map[x][y]);
    DFS(x+1,y-1,cnt+Map[x][y]);
}*/
int main()
{
    //freopen("T4data.in","r",stdin);
    char c;
    ios::sync_with_stdio(false);
    cin>>n>>m>>k;
    for(int i=1;i<=n;i++)
    {
        for(int j=1;j<=m;j++)
        {
            cin>>c;
            Map[i][j]=c-'0';
        }
    }
    /*for(int i=1;i<=n;i++)
    {
        for(int j=1;j<=m;j++)cout<<Map[i][j]<<" ";
        cout<<endl;
    }*/
    for(int i=1;i<=m;i++)
    {
        dp[1][i][Map[1][i]]=1;
    }
    for(int i=2;i<=n;i++)
    {
        for(int j=1;j<=m;j++)
        {
            for(int kk=Map[i][j];kk<=n*9;kk++)
            {
                dp[i][j][kk]=dp[i-1][j-1][kk-Map[i][j]] || dp[i-1][j+1][kk-Map[i][j]];
            }
        }
    }
    /*for(int i=1;i<=n;i++)
    {
        for(int j=1;j<=m;j++)
        {
            for(int kk=1;kk<=n*9;kk++)cout<<dp[i][j][kk]<<" ";
            cout<<endl;
        }
    }*/
    for(int i=n*9;i>=1;i--)
    {
        if(i%(k+1))continue;
        for(int j=1;j<=m;j++)
        {
            if(dp[n][j][i])
            {
                cout<<i<<endl;
                return 0;
            }
        }
    }
    cout<<-1<<endl;
    //for(int i=1;i<=m;i++)DFS(1,i,0);
    //cout<<ans<<endl;
    return 0;
}

\[\color{red}\large\text{完結撒花}\]

相關文章
相關標籤/搜索