有重字符串字典序第k排列

纯模拟规律。。逐步确定每一位。

#include<stdio.h>
#include<string.h>
#include<algorithm>
using namespace std;
#define ll long long
ll used[17];
ll f[27],ans[38];
ll sum[20];
ll len;
char str[21];
ll Jc()
{
    ll s=1,i;
    ll x[28];
    memset(x,0,sizeof(x));
    for(i=1;i<=len;i++)
          if(ans[str[i]-'A']!=0&&!used[i]&&!x[str[i]-'A'])
            {
                s*=f[ans[str[i]-'A']];
                x[str[i]-'A']=1;
            }
    return s;

}
int main()
{

    ll k;
    while(scanf("%s%lld",str,&k)!=EOF)
    {
        ll i,j;
        if(k==0&&str[0]=='#') break;
         len=strlen(str);
        memset(used,0,sizeof(used));
        sort(str,str+len);
        for(i=len;i>=1;i--)
            str[i]=str[i-1];
        ll n=len;
        memset(ans,0,sizeof(ans));
        for(i=1;i<=n;i++)
        {
            int v=str[i]-'A';
            ans[v]+=1;

        }

        f[1]=1;
        for(i=2;i<n;i++)
            f[i]=i*f[i-1];
        for(i=1;i<n;i++)
        {
            sum[0]=0;
            int u=0,q=0;
            for(j=1;j<=n;j++)
            {

                if(used[j]) continue;
                if(str[j]==str[q]&&u!=0)
                    continue;

                else
                {
                    u++;
                    q=j;
                    ans[str[j]-'A']-=1;
                    sum[u]=f[n-i]/Jc()+sum[u-1];

                    ans[str[j]-'A']+=1;
                }
                if(sum[u]>=k)
                {
                    printf("%c",str[j]);
                    ans[str[j]-'A']-=1;
                    used[j]=1;

                    k-=sum[u-1];
                    break;
                }
            }
        }
        for(i=1;i<=n;i++)
            if(!used[i])
             printf("%c",str[i]);
        printf("\n");
    }
    return 0;
}

时间: 2024-10-05 05:42:10

有重字符串字典序第k排列的相关文章

poj_1037 动态规划+字典序第k大

题目大意 给定n个数字,规定一种 cute 排序:序列中的数字大小为严格的波浪形,即 a[0] > a[1] < a[2] > a[3] < .... 或者 a[0] < a[1] > a[2] < a[3] ......对于N个数字来说,可以构成多个cute序列,这些序列按照字典序进行排序,求出第k个序列. 题目分析 一.求字典序的第i个排列 直接一位一位枚举答案!从前到后枚举求得每一位:枚举一位时,计算在这样的前缀下,后面的总的排列数.如果严格小于总编号,则该

hdu 5008 查找字典序第k小的子串

Boring String Problem Time Limit: 6000/3000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)Total Submission(s): 1848    Accepted Submission(s): 492 Problem Description In this problem, you are given a string s and q queries. For each qu

实现一个函数,可以左旋字符串中的k个字符

实现一个函数,可以左旋字符串中的k个字符. AABCD左旋一个字符得到ABCDA AABCD左旋两个字符得到BCDAA #include<stdio.h>  #include<stdlib.h>  void spin(char arr[],int num) //spin函数用以完成旋转字符的功能  {  char arr1[5] = {0};  char *str = arr; //创建两个指针都指向原字符数组的首地址  char *start = arr;  char *mov 

C语言--左旋字符串中的K个字符

问题: 3.实现一个函数,可以左旋字符串中的k个字符. AABCD左旋一个字符得到ABCDA AABCD左旋两个字符得到BCDAA #include<stdio.h> #include<assert.h> #include<string.h> void reserve(char* str, int len) { assert(str); char* start = str; char* end = str + len - 1; while (start < end

求得到一个字符串@“absdfasdfsdfdsafsd....”所有的排列

//得到一个字符串@“absdfasdfsdfdsafsd....”所有的排列 length!/((相同项)!*(相同项)!) -(int )numberOfstring:(NSString*)str // NSString *str [email protected]"adfsadfasdfasdfsadfsdaxfgghfgjtyy"; int sumlength = str.length;//所有字符的个数 NSString *mystr = @"abcdefghijk

给定两个字符串,确定其中一个字符串的字符重新排列后,能否变成另一个字符串

1 /* 2 * 给定两个字符串,确定其中一个字符串的字符重新排列后,能否变成另一个字符串,其实也就是变位词问题 3 * 比如说 a='abc' b='acb'是可以通过a变成b的 4 * 思路; 5 * 1.应进行分析,变位词区分大小写吗?比如God和dog是变位词?还需要考虑空格问题? 6 * 在这里我们假定是区分大小写的. 7 * 2.比较两个字符串时,如果它们的长度都不相等了,那肯定不是变位词 8 * 9 * 10 * */ 11 12 public class IsSameString

实现一个函数,可以左旋字符串中的k个字符。

题目:实现一个函数,可以左旋字符串中的k个字符. ABCD左旋一个字符得到BCDA ABCD左旋两个字符得到CDAB 方法一:直接旋转void left_move(chararr, int k)//左旋字符串{char tmp = 0;charp = arr;while (k!=0){tmp =p;while ((p+1) != '\0'){p = (p + 1);p++;}*p = tmp;k--;}} 方法二:void left_move2(char*arr, int k)//更优解法//要

面试:字符串字典序最大的子序列

字符串字典序最大的子序列 首先要知道什么是字典序,顾名思义,就是字典上的顺序.两个字符串进行对比时, 一位一位的按照a, b, c等字典序比较,如果相同就顺位比较下一位,比如ba比ab大,如果哪一位已经不一样 就已经比较出来结果了,如果是abc, abcd这样的情况,长度长的大. 子序列和子串的区别:这俩其实不一样,子串是连续的,比如字符串abcdef,它的子串是abc,abcd等这些连续的.而子序列是不连续的.比如ace这样的. 最简单的想法,先遍历一遍,找到最大的一个字符,以及他的位置,然后

PHP_字典序法获得排列组合

前段时间一次聚会闲聊时聊到一个问题,就是给你一排数组,例如1,2,3,4,5,如何能高效的获取上述数列的所有排列组合,正巧没事,研究了一下,一开始以为是个很简单的问题,就直接开始写代码了,后来发现怎么循环也不理想,基本上都有一些不必要的消耗,百度一下看到一个不错的算法,字典序法,顺便学习一下,然后记录之. 摘一段算法思想: 设P是[1,n]的一个全排列. P=P1P2-Pn=P1P2-Pj-1PjPj+1-Pk-1PkPk+1-Pn , j=max{i|Pi<Pi+1}, k=max{i|Pi>