poj 3590 The shuffle Problem(置换群的幂运算)

Problem Link

poj 3590 The shuffle Problem
题目很简单,求一个 n 阶置换 T
Tk=e,s.tk ,最大,其中 k 使得 T ,第一次等于 e 的值

Analysis

对于一个置换来说, k T 的每个循环的循环节的最小公倍数。
所以对于 n 我们的目标就是找到一些素数的幂,使其和为 n 并且,乘积最大。由于 n 为100,100以内的素数只有25个,我们可以采用爆搜的方法,所有所最优解。

AC code

Source Code

Problem: 3590       User: taotao
Memory: 692K        Time: 0MS
Language: G++       Result: Accepted
Source Code
#include
#include
#include
#include
#include

using namespace std;
typedef long long LL;
const int maxn = 1111;

int prime[110],primecnt;

void sieve()
{
    memset(prime,1,sizeof(prime));
    primecnt = 0;
    for(int i=2 ; i<=100 ; ++i)
    {
        if(prime[i])
        {
            prime[primecnt++] =i;
            for(int j = i*i ; j<=100 ; j+=i)
                prime[j] = 0;
        }
    }

}

int step[100],maxlcm = 0;
vector<int> ans;
void dfs(int remain,int cur)
{
    if(remain int lcm = 1;
        for(int i = 0 ; iif(step[i])lcm*=step[i];
        if(maxlcmfor(int i=0 ; iif(step[i])ans.push_back(step[i]);
           while(remain--)ans.push_back(1);
        }
    }else{
        step[cur] = 0;
        if(cur+11);
        for(step[cur] = prime[cur] ; step[cur]<=remain ; step[cur]*=prime[cur])
            if(cur+11);
    }
}


int main()
{
    //freopen("H:\\c++\\file\\stdin.txt","r",stdin);
    //freopen("H:\\c++\\file\\stdout.txt","w",stdout);

    sieve();
    int n;
    int T ;scanf("%d",&T);
    while(T--)
    {
        maxlcm = 0;
        memset(step,0,sizeof(step));
        scanf("%d",&n);
        ans.clear();
        dfs(n,0);
       printf("%d",maxlcm);
       sort(ans.begin(),ans.end());
       int last  = 0;
       for(int i=0 ; iint k = ans[i];
           int j = last+2;
           while(k>1)
           {
               printf(" %d",j);j++;k--;
           }
           printf(" %d",last+1);
           last +=ans[i];
       //for(int i=0 ; i
        }
        printf("\n");
    }

    return 0;
}

你可能感兴趣的:(置换群的幂运算,算法刷题)