AtCoder Beginner Contest 436

链接:https://atcoder.jp/contests/abc436

A – o-padding 

算法:

    模拟。

思路:

    无。

关键代码:

void miyan()
{
    int n;
    string s;
    cin >> n >> s;

    cout << string(n - s.size(), 'o') << s << endl;
}

B – Magic Square 

算法:

    模拟。

思路:

    无。

关键代码:

void miyan()
{
    int n;
    cin >> n;
    vector<vector<int>> a(n, vector<int>(n, 0));

    a[0][(n - 1) / 2] = 1;

    int last = 1;
    int x = 0, y = (n - 1) / 2;
    for (int i = 0; i < n * n - 1; ++i)
    {
        if (a[(x - 1 + n) % n][(y + 1) % n] == 0)
        {
            x = (x - 1 + n) % n;
            y = (y + 1) % n;

            a[x][y] = ++last;
        }
        else
        {
            x = (x + 1) % n;
            a[x][y] = ++last;
        }
    }

    for (int i = 0; i < n; ++i)
    {
        for (int j = 0; j < n; ++j)
            cout << a[i][j] << ' ';

        cout << endl;
    }
}

C – 2×2 Placing 

算法:

    模拟,\(stl\)。

思路:

    将放置了方块的点加入到 \(set\) 或者 \(map\) 中,每次放置只需在 \(set\) 或者 \(map\) 中查找四个点上是否有方块即可。

关键代码:

void miyan()
{
    int n, m;
    cin >> n >> m;

    ll ans = 0;

    map<pii, int> hash;
    for (int i = 0; i < m; ++i)
    {
        int x, y;
        cin >> x >> y;

        if (!hash.count({x, y}) && !hash.count({x, y + 1}) && !hash.count({x + 1, y}) && !hash.count({x + 1, y + 1}))
        {
            ++ans;
            hash[{x, y}] = 1;
            hash[{x, y + 1}] = 1;
            hash[{x + 1, y}] = 1;
            hash[{x + 1, y + 1}] = 1;
        }
    }

    cout << ans << endl;
}

D – Teleport Maze 

算法:

    \(bfs\)。

思路:

    每个传送点只到达一次。

关键代码:

void miyan()
{
    int n, m;
    cin >> n >> m;
    vector<string> g(n);
    for (auto &x : g)
        cin >> x;

    vector<vector<pii>> c(26);
    for (int i = 0; i < n; ++i)
    {
        for (int j = 0; j < m; ++j)
        {
            if (g[i][j] >= 'a' && g[i][j] <= 'z')
            {
                c[g[i][j] - 'a'].push_back({i, j});
            }
        }
    }

    vector<int> st(26, 0);
    vector<vector<int>> dist(n, vector<int>(m, 1e9));
    queue<pii> q;
    q.push({0, 0});
    dist[0][0] = 0;

    while (q.size())
    {
        auto [x, y] = q.front();
        q.pop();

        if (x == n - 1 && y == m - 1)
        {
            cout << dist[x][y] << endl;
            return;
        }

        if (g[x][y] >= 'a' && g[x][y] <= 'z' && !st[g[x][y] - 'a'])
        {
            st[g[x][y] - 'a'] = 1;

            for (auto [a, b] : c[g[x][y] - 'a'])
            {
                if (dist[a][b] > dist[x][y] + 1)
                {
                    dist[a][b] = dist[x][y] + 1;
                    q.push({a, b});
                }
            }
        }

        for (int i = 0; i < 4; ++i)
        {
            int a = x + dx[i], b = y + dy[i];
            if (a < 0 || a >= n || b < 0 || b >= m || g[a][b] == '#')
                continue;

            if (dist[a][b] > dist[x][y] + 1)
            {
                dist[a][b] = dist[x][y] + 1;
                q.push({a, b});
            }
        }
    }

    cout << -1 << endl;
}

E – Minimum Swap 

算法:

    \(dsu\)。

思路:

    猜的。

    将 \(i\) 和 \(a[i]\) 所在集合合并,对于一个集合中可以作为第一次交换的次数为 \(C_{size}^{2}\)。

关键代码:

void miyan()
{
    int n;
    cin >> n;
    vector<int> a(n);
    for (int i = 1; i <= n; ++i)
        cin >> a[i];

    vector<ll> p(n + 1), siz(n + 1, 1);
    for (int i = 1; i <= n; ++i)
        p[i] = i;

    auto find = [&](auto &&self, int x) -> int
    {
        if (x != p[x])
            p[x] = self(self, p[x]);
        return p[x];
    };

    for (int i = 1; i <= n; ++i)
    {
        int x = i, y = a[i];

        x = find(find, x), y = find(find, y);
        if (x != y)
        {
            siz[x] += siz[y];
            p[y] = x;
        }
    }

    ll ans = 0;
    for (int i = 1; i <= n; ++i)
        if (i == find(find, i) && siz[i] > 1)
            ans += siz[i] * (siz[i] - 1) / 2;

    cout << ans << endl;
}

F – Starry Landscape Photo 

算法:

    树状数组。

思路:

    首先肯定不能暴力求出所有 \([l, r, b]\)。

    考虑升序枚举 \(b\),找到所有满足条件的 \(l, r\)。

    根据乘法原理,对于一个 \(b\) 满足条件的区间个数为 \(l * r\) 个。

    使用树状数组动态维护坐标点上是否有值。

关键代码:

int n;
vector<int> tr;

void add(int x)
{
    for (; x <= n; x += x & -x)
        ++tr[x];
}

ll query(int x)
{
    ll ans = 0;
    for (; x; x -= x & -x)
        ans += tr[x];

    return ans;
}

void miyan()
{
    cin >> n;
    vector<int> a(n + 1), pos(n + 1);
    for (int i = 1; i <= n; ++i)
    {
        cin >> a[i];
        pos[a[i]] = i;
    }

    tr.resize(n + 1, 0);

    ll ans = 0;
    for (int i = 1; i <= n; ++i)
    {
        add(pos[i]);

        ll L = query(pos[i]);
        ll R = i - L + 1;

        ans += L * R;
    }

    cout << ans << endl;
}

G – Linear Inequation 

    还没补。

暂无评论

发送评论 编辑评论


				
|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ °Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
颜文字
Emoji
小恐龙
花!
上一篇
下一篇