1. 程式人生 > >CCF模擬題-1~5

CCF模擬題-1~5

報名第九次CCF認證,是為了能參加第二屆的CCSP,做了一下題庫裡的C\C++模擬,發現真是夠水了……

前三題,過於簡單,不再贅述,發一下題目和對應答案~~~

出現次數最多的數

1

#include <iostream>
#include <algorithm>
#include <cstdio>

using namespace std;

const int MAXN = 1010;

int S[MAXN];

int main(int argc, const char * argv[])
{
    int n;
    cin >> n;

    for
(int i = 0; i < n; i++) { scanf("%d", S + i); } sort(S, S + n); int res = S[0], times = 1, res_ = S[0], times_ = 1; for (int i = 1; i < n; i++) { if (S[i] == S[i - 1]) { times_++; } else { res_ = S[i]; times_ = 1
; } if (times_ > times) { res = res_; times = times_; } } cout << res << '\n'; return 0; }

ISBN號碼

2

#include <iostream>
#include <cstdio>

using namespace std;

const int MAXN = 10;
const int MOD = 11
; int ISBN[MAXN]; char X; int main(int argc, const char * argv[]) { scanf("%1d-%1d%1d%1d-%1d%1d%1d%1d%1d-%c", ISBN + 0, ISBN + 1, ISBN + 2, ISBN + 3, ISBN + 4, ISBN + 5, ISBN + 6, ISBN + 7, ISBN + 8, &X); int sum = 0; for (int i = 0; i < 9; i++) { sum += ISBN[i] * (i + 1); } sum %= MOD; int num = X == 'X' ? 10 : X - '0'; if (num == sum) { cout << "Right\n"; } else { cout << ISBN[0] << '-'; cout << ISBN[1] << ISBN[2] << ISBN[3] << '-'; cout << ISBN[4] << ISBN[5] << ISBN[6] << ISBN[7] << ISBN[8] << '-'; if (sum == 10) { cout << "X\n"; } else { cout << sum << '\n'; } } return 0; }

最大的矩陣

3

#include <iostream>
#include <cstdio>

using namespace std;

const int MAXN = 1010;

int h[MAXN];

int main(int argc, const char * argv[])
{
    int n;
    cin >> n;

    for (int i = 0; i < n; i++)
    {
        scanf("%d", h + i);
    }

    int res = 0;
    for (int i = 0; i < n; i++)
    {
        int j, k;
        for (j = i - 1; j >= 0; j--)
        {
            if (h[j] < h[i])
            {
                j++;
                break;
            }
        }
        if (j == -1)
        {
            j++;
        }
        for (k = i + 1; k < n; k++)
        {
            if (h[k] < h[i])
            {
                k--;
                break;
            }
        }
        if (k == n)
        {
            k--;
        }
        int temp = (k - j + 1) * h[i];
        if (temp > res)
        {
            res = temp;
        }
    }

    cout << res << '\n';

    return 0;
}

有趣的數

4

遇見這種問題,不用多想,百分之八九十就是dp,觀察數位之間的關係,尋找狀態轉移方程,具體的狀態轉移方程看程式碼~~~不難理解。

#include <iostream>

using namespace std;

typedef long long ll;

const int MAXN = 1010;
const ll MOD = 1e9 + 7;
const int MAXM = 6;

ll dp[MAXN][MAXM];

int main()
{
    int n;
    cin >> n;

    for (int i = 0; i < MAXM; i++)
    {
        dp[0][i]=0;
    }
    /*6種狀態
     * 0--剩013
     * 1--剩13
     * 2--剩01
     * 3--剩3
     * 4--剩1
     * 5--無
     */
    for (int i = 1; i <= n; i++)
    {
        int temp = i - 1;
        dp[i][0] = 1;
        dp[i][1] = (dp[temp][0] + dp[temp][1] * 2) % MOD;
        dp[i][2] = (dp[temp][0] + dp[temp][2]) % MOD;
        dp[i][3] = (dp[temp][1] + dp[temp][3] * 2) % MOD;
        dp[i][4] = (dp[temp][1] + dp[temp][2] + dp[temp][4] * 2) % MOD;
        dp[i][5] = (dp[temp][3] + dp[temp][4] + dp[temp][5] * 2) % MOD;
    }

    cout << dp[n][5] << endl;

    return 0;
}

I’m stuck!

5

這道題是常規的搜尋題,思路就是dfs或者bfs,並且需要滿足兩個條件,而這兩個條件我們可以分別先滿足,然後把同時滿足的計數,一般做法是先正向dfs一遍,然後把所有S能達到的方格再dfs一遍,但是這樣的話時間代價太高,不知道會不會超時,比較快捷的解法就是先正向,然後反向,正向十分簡單,反向比較難想一些,考到逆向思維,你需要判斷是否可以原路折返回去,而這裡就需要判斷上一步的格子和這一步的格子之間的連通性,程式碼寫起來比較費勁兒,需要考慮很多種情況,具體的還是看程式碼吧~~~

#include <iostream>
#include <cstring>

using namespace std;

const int MAXR = 55;
const int MAXC = MAXR;
const int dir[4][2] = {{-1, 0}, {1, 0}, {0, -1}, {0, 1}};

int R, C;
char map[MAXR][MAXC];
int visS[MAXR][MAXC];
int visT[MAXR][MAXC];
bool flag;

void dfsS(int x, int y)
{
    visS[x][y] = 1;

    switch (map[x][y])
    {
        case '+':
            for (int i = 0; i < 4; i++)
            {
                if (x + dir[i][0] >= 0 && x + dir[i][0] < R &&
                    y + dir[i][1] >= 0 && y + dir[i][1] < C &&
                    map[x + dir[i][0]][y + dir[i][1]] != '#' &&
                    visS[x + dir[i][0]][y + dir[i][1]] == 0)
                {
                    dfsS(x + dir[i][0], y + dir[i][1]);
                }
            }
            break;
        case '-':
            for (int i = 2; i < 4; i++)
            {
                if (x + dir[i][0] >= 0 && x + dir[i][0] < R &&
                    y + dir[i][1] >= 0 && y + dir[i][1] < C &&
                    map[x + dir[i][0]][y + dir[i][1]] != '#' &&
                    visS[x + dir[i][0]][y + dir[i][1]] == 0)
                {
                    dfsS(x + dir[i][0], y + dir[i][1]);
                }
            }
            break;
        case '|':
            for (int i = 0; i < 2; i++)
            {
                if (x + dir[i][0] >= 0 && x + dir[i][0] < R &&
                    y + dir[i][1] >= 0 && y + dir[i][1] < C &&
                    map[x + dir[i][0]][y + dir[i][1]] != '#' &&
                    visS[x + dir[i][0]][y + dir[i][1]] == 0)
                {
                    dfsS(x + dir[i][0], y + dir[i][1]);
                }
            }
            break;
        case '.':
            if (x + 1 < R && map[x + 1][y] != '#' && visS[x + 1][y] == 0)
            {
                dfsS(x + 1, y);
            }
            break;
    }
}

void dfsT(int x, int y, int preX, int preY)
{
    if (visT[x][y] || map[x][y] == '#')
    {
        return ;
    }

    if (map[x][y] == '.' && preX == x + 1 && preY == y)
    {
        visT[x][y] = 1;
    }
    else if (map[x][y] == '-' && preX == x)
    {
        visT[x][y] = 1;
    }
    else if (map[x][y] == '|' && preY == y)
    {
        visT[x][y] = 1;
    }
    else if (map[x][y] == '+')
    {
        visT[x][y] = 1;
    }

    if (visT[x][y] == 0)
    {
        return ;
    }

    if (x - 1 >= 0)
    {
        dfsT(x - 1, y, x, y);
    }
    if (x + 1 < R)
    {
        dfsT(x + 1, y, x, y);
    }
    if (y - 1 >= 0)
    {
        dfsT(x, y - 1, x, y);
    }
    if (y + 1 < C)
    {
        dfsT(x, y + 1, x, y);
    }
}

int main(int argc, const char * argv[])
{
    memset(visS, 0, sizeof(visS));
    memset(visT, 0, sizeof(visT));

    cin >> R >> C;

    int xS = 0, xT = 0, yS = 0, yT = 0;
    for (int i = 0; i < R; i++)
    {
        scanf("%s", map[i]);
        for (int j = 0; j < C; j++)
        {
            if (map[i][j] == 'S')
            {
                xS = i;
                yS = j;
                map[i][j] = '+';
            }
            else if (map[i][j] == 'T')
            {
                xT = i;
                yT = j;
                map[i][j] = '+';
            }
        }
    }

    dfsS(xS, yS);

    if (visS[xT][yT] == 0)
    {
        cout << "I'm stuck!\n";
        return 0;
    }

    dfsT(xT, yT, xT, yT);

    int counts = 0;

    for (int i = 0; i < R; i++)
    {
        for (int j = 0; j < C; j++)
        {
            if (map[i][j] != 'S' && map[i][j] != 'T' &&
                visS[i][j]  && !visT[i][j])
            {
                counts++;
            }
        }
    }

    std::cout << counts << '\n';

    return 0;
}

前三題就是秀智商的問題,不算笨的人30分鐘內就能搞定前三題,拿到300分,第四題、第五題需要略微思考些,就算拿不全分,也不至於0分~~~