Codeforces Round #753 (Div. 3)


Codeforces Round #753 (Div. 3)

A. Linear Keyboard

思路分析:

  • 無語了,題目總是讀不順,看到output那個minimal我還以為是把手放到一個單詞上,看需要多少time來完成敲出字符串。
  • 寫完一看,答案不對勁,然后發現這題其實就是把字母表重新排一下,然后求兩個字母間的距離之差的絕對值。

代碼

#include <bits/stdc++.h>
using namespace std;
map<char, int> mp;
int main()
{
        ios::sync_with_stdio(0);
        cin.tie(0);
        cout.tie(0);
        int t;
        cin >> t;
        while (t--)
        {
                string s;
                cin >> s;
                for (int i = 0; i < s.size(); i++)
                {
                        mp[s[i]] = i + 1;
                }
                string t;
                cin >> t;
                int ans = 0;
                for (int i = 1; i < t.size(); i++)
                {
                        ans += abs(mp[t[i]] - mp[t[i - 1]]);
                }
                cout << ans << endl;
        }
        return 0;
}

B. Odd Grasshopper

思路分析:

  • 這個題目其實是找規律題,並且只和一開始給你的第一個值的奇偶有關。
  • 如果給你的是偶數,那么就是-,+,+,-,-,+,+,-,-......
  • 如果給你的是奇數,那么就是+,-,-,+,+,-,-,+,+......
  • 我們可以看出除了第一個之外,后面每四個加起來都有規律,偶數時是-4,奇數時是4......
  • 然后就是分析剩下來不能成為一組的,那么找一下規律即可。

代碼

#include <bits/stdc++.h>
using namespace std;
#define ll long long
int main()
{
        ios::sync_with_stdio(0);
        cin.tie(0);
        cout.tie(0);
        int t;
        cin >> t;
        while (t--)
        {
                ll x, n;
                cin >> x >> n;
                if (n == 0)
                {
                        cout << x << endl;
                }
                else
                {
                        if (x % 2 == 0)
                        {
                                x--;
                                n--;
                                x = x + n / 4 * (-4);
                                if (n % 4 == 0)
                                {
                                        cout << x << endl;
                                }
                                else if (n % 4 == 1)
                                {
                                        x += (n + 1);
                                        cout << x << endl;
                                }
                                else if (n % 4 == 2)
                                {
                                        x += (2 * n + 1);
                                        cout << x << endl;
                                }
                                else if (n % 4 == 3)
                                {
                                        x += (n - 2);
                                        cout << x << endl;
                                }
                        }
                        else
                        {
                                x++;
                                n--;
                                x = x + n / 4 * 4;
                                if (n % 4 == 0)
                                {
                                        cout << x << endl;
                                }
                                else if (n % 4 == 1)
                                {
                                        x -= (n + 1);
                                        cout << x << endl;
                                }
                                else if (n % 4 == 2)
                                {
                                        x -= (2 * n + 1);
                                        cout << x << endl;
                                }
                                else if (n % 4 == 3)
                                {
                                        x -= (n - 2);
                                        cout << x << endl;
                                }
                        }
                }
        }
        return 0;
}

C. Minimum Extraction

思路分析:

  • 我們要求的是在刪減過程中數組最小值的最大值。
  • 首先我們肯定是要排序的,然后依次求最小值出來,可以肯定的是我們從最小的開始選的話,在這個過程中每個數都會減去之前刪的那個數,在刪到某個數前,它必然會變成他和前面那個數的差值,因為,我們從第一個開始,到刪到它前面一個數時,這兩個數的差值一直沒變,所以最大的最小值其實就是排序后的數組的兩兩相鄰數的差值的最大值。

代碼

#include <bits/stdc++.h>
using namespace std;

const int maxn = 2e5 + 10;
int a[maxn];

int main()
{
        ios::sync_with_stdio(0);
        cin.tie(0);
        cout.tie(0);
        int t;
        cin >> t;
        while (t--)
        {
                int n;
                cin >> n;
                for (int i = 1; i <= n; i++)
                {
                        cin >> a[i];
                }
                sort(a + 1, a + 1 + n);
                int ans = -1000000001;
                for (int i = 1; i <= n; i++)
                {
                        ans = max(ans, a[i] - a[i - 1]);
                }
                cout << ans << endl;
        }
        return 0;
}

D. Blue-Red Permutation

思路分析:

  • 這個題目其實就是貪心,我們這樣想,先把blue顏色的num放到前面,因為它們只能變小或者不變而不能變大,我們要得到的是一個\(1 - n\)的排列,也就是說得到的數組的值中\(1 - n\)這些數必然出現並且一個只出現一次。
  • 那么我們把可以變小的num先放到前面(同顏色的按值大小排序,顯然值越小越排到前面)。
  • 然后就是定義一個tmp來表示當前要造的數,如果我們遍歷數組時,它比tmp大而且它只能變大,那肯定就是不對的、如果它比tmp小並且它只能變小,也是不對的。

代碼

#include <bits/stdc++.h>
using namespace std;
const int maxn = 2e5 + 10;
struct node
{
        int val;
        char ch;
} a[maxn];

bool cmp(node a, node b)
{
        if (a.ch != b.ch)
                return a.ch < b.ch;
        return a.val < b.val;
}
int main()
{
        ios::sync_with_stdio(0);
        cin.tie(0);
        cout.tie(0);
        int t;
        cin >> t;
        while (t--)
        {
                int n;
                cin >> n;
                for (int i = 1; i <= n; i++)
                {
                        cin >> a[i].val;
                }
                for (int i = 1; i <= n; i++)
                {
                        cin >> a[i].ch;
                }
                sort(a + 1, a + 1 + n, cmp);
                bool flag = 1;
                int tmp = 1;
                for (int i = 1; i <= n; i++)
                {
                        if (a[i].val < tmp && a[i].ch == 'B')
                        {
                                flag = 0;
                                break;
                        }
                        else if (a[i].val > tmp && a[i].ch == 'R')
                        {
                                flag = 0;
                                break;
                        }
                        else
                        {
                                tmp++;
                        }
                }
                if (flag)
                {
                        cout << "YES" << endl;
                }
                else
                {
                        cout << "NO" << endl;
                }
        }
        return 0;
}

E. Robot on the Board 1

思路分析:

  • 這題是看dalao代碼學的,首先我們可以這樣想,我們拿出四根線,分別放置在矩陣上下左右外,也就是放在外面,然后每次我們都更新一下上下左右邊界,記錄邊界。
  • 然后就是什么時候輸出,第一種情況當然是現在左右(上下)邊界相差大於\(2\)(那么我們只需要選上左邊界相夾的那一塊的坐標即可。),第二種情況就是至少有兩個邊界(l和r 或者 u和d)相差為\(1\)了,那么這個時候我們不能再更新答案了,因為那兩個邊界中間已經沒有塊可選了,所以只要輸出上一次的答案即可。

代碼

#include <bits/stdc++.h>
using namespace std;

int main()
{
        ios::sync_with_stdio(0);
        cin.tie(0);
        cout.tie(0);
        int t;
        cin >> t;
        while (t--)
        {
                int n, m;
                cin >> n >> m;
                string s;
                cin >> s;
                pair<int, int> a;
                a = {1, 1};
                bool flag = 0;
                int l = 0, r = m + 1, u = 0, d = n + 1;
                int suml = 0, sumr = 0, sumu = 0, sumd = 0;
                for (int i = 0; i < s.size(); i++)
                {
                        if (s[i] == 'R')
                        {
                                sumr++;
                        }
                        else if (s[i] == 'L')
                        {
                                suml++;
                        }
                        else if (s[i] == 'U')
                        {
                                sumu++;
                        }
                        else if (s[i] == 'D')
                        {
                                sumd++;
                        }
                        l = max(l, suml - sumr);
                        r = min(r, m + 1 - (sumr - suml));
                        u = max(u, sumu - sumd);
                        d = min(d, n + 1 - (sumd - sumu));
                        if (l + 1 >= r || u + 1 >= d)
                        {
                                flag = 1;
                                cout << a.first << ' ' << a.second << endl;
                                break;
                        }
                        else
                        {
                                a = {u + 1, l + 1};
                        }
                }
                if (!flag)
                        cout << a.first << " " << a.second << endl;
        }
        return 0;
}


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM