排列

排列

https://ac.nowcoder.com/acm/contest/7225/A

快速幂思想

题目描述
牛牛拿到了一个长度为N的排列和M个区间,一开始排列是1、2、3......N。
然后他将这些区间在按顺序在排列上翻转,全部翻转一遍称一次操作。
现在他要去搞文化了...所以拜托你告诉他经过K次操作后的排列长什么样子。

题目分析
刚刚开始看题目的时候一脸懵逼,没看懂题目的意思,不过想想毕竟是第一题应该简单一些,所以就再次再次的看题目,发现:m次操作代表的是一次总的操作,也就是说要做k次m次的操作就是最终答案,但是题目给出的范围很大,所以需要用倍增的思想,倍增的思想能很快地实现计算,所以我们引进快速幂思想去分析题目

#include <bits/stdc++.h>
using namespace std;
const int maxn = 1e6 + 10;
int ans[maxn], temp[maxn], mode[maxn];
int n, m, k;
void solve(int a[], int b[])
{
    for (int i = 1; i <= n; ++i)
        temp[i] = b[i]; //防止a和b为同一数组时修改自身。
    for (int i = 1; i <= n; ++i)
        a[i] = temp[a[i]];
}
void fastpow()
{
    int t = k;
    while (t)
    {
        if (t & 1)
            solve(ans, mode);
        solve(mode, mode);
        t >>= 1;
    }
}
int main()
{
    scanf("%d%d%d", &n, &m, &k);
    for (int i = 1; i <= n; ++i)
        ans[i] = mode[i] = i;
    int l, r;
    while (m--)
    {
        scanf("%d%d", &l, &r);
        while (l < r)
            swap(mode[l++], mode[r--]);
    }
    fastpow();
    for (int i = 1; i <= n; ++i)
        printf("%d ", ans[i]);
    return 0;
}
牛客比赛系列题解 文章被收录于专栏

加油加油

全部评论

相关推荐

评论
点赞
收藏
分享
牛客网
牛客企业服务