• 51nod 1384 可重集的全排列


    对于1231,121,111等有重复的数据,我们怎么做到生成全排列呢

    实际上,对于打标记再释放标记的这种方法,如果一开始第一层递归访问过1那么你再访问

    就会完全重复上一次1开头的情况,那么递归地考虑这件事,我们发现不需要重复相同的开头

    但这样可能会重复一个数字过多次数,比如121,第一层2,第二层可能是2,第三层可能也是2

    那么我们怎么解决这个呢,一个笨办法是统计原数组该值出现几次,现有生成的数列里出现了几次,

    那么比较一下大小,我们就知道能不能放

    关于不放重复开头这件事,我们可以对原序列排序,于是相同的值相邻,那么我们在实现中,每次跳过相同的一段即可

    附上代码,由于输出量巨大,所以...cstdio TLE,stdio.h AC

     1 #include <stdio.h>
     2 #include <cstring>
     3 #include <algorithm>
     4 using namespace std;
     5 char s[100];
     6 int num[100],sz,A[100]; 7 void dfs(int cur){
     8     if(cur==sz){
     9         for(int i=0;i<sz;++i) printf("%d",A[i]);printf("
    ");
    10     }
    11     else for(int i=0;i<sz;++i){
    12         if(!i||(num[i]!=num[i-1])){
    13             int c1=0,c2=0;
    14             for(int j=0;j<cur;++j) if(num[i]==A[j]) c1++;
    15             for(int j=0;j<sz;++j) if(num[i]==num[j]) c2++;
    16             if(c1<c2){
    17                 A[cur]=num[i];dfs(cur+1);
    18             }
    19         }
    20     }
    21 }
    22 int main(){
    23     scanf("%s",s);
    24     sz=strlen(s);
    25     for(int i=0;i<sz;++i) num[i]=s[i]-'0';
    26     sort(num,num+sz);
    27     dfs(0);
    28     return 0;
    29 }
  • 相关阅读:
    Chap5:操作文件和目录[The Linux Command Line]
    ABC3
    ABC2
    ABC
    Spring MVC / Boot
    Usefull Resources
    [ Learning ] Design Pattens
    [ Learning ] Spring Resources
    URL Resources
    [ Windows BAT Script ] BAT 脚本获取windows权限
  • 原文地址:https://www.cnblogs.com/linkzijun/p/6920370.html
Copyright © 2020-2023  润新知