【问题标题】:figure out all derangement of array找出数组的所有紊乱
【发布时间】:2020-06-20 15:51:22
【问题描述】:

这是一个试图找出数组{10, 11, 12, 13}的所有紊乱的程序

但它不起作用,因为当涉及到 depth==0, i==0Peano[]=={0, 1, 2, 3} 时,for 循环没有结束,然后 i 递减为 -1。这是怎么回事?

      #include<stdio.h>
        #include<stdlib.h>
        unsigned long long derange(int *array, int LEN, _Bool display, int *Peano, unsigned depth);
        int main(void){
        int i ,LEN=4, *Peano=malloc(sizeof(int));
        int array[4]={10,11,12,13};
        for(i=0; i<LEN; i++)Peano[i]=i;
        derange(array, LEN, 1, Peano, 0);
        printf("this derangement of the array total of %llu.\n", derange(array, LEN, 0, Peano, 0));
        return 0;}

            unsigned long long derange(int *array, int LEN, _Bool display, int *Peano, unsigned depth){
                    int i, temp;
                    unsigned long long count=0;
                    if(depth==LEN){
                            if(display){
                                    for(i=0; i<LEN; i++)
                                            fprintf(stdout, "%d\040", array[i]);
                                    putchar('\n');}
                            return 1;}
                    for(i=LEN-1; i>=depth; i--){
                            if(i==Peano[depth])continue;
                            temp=Peano[i]; Peano[i]=Peano[depth]; Peano[depth]=temp;
                            temp=array[i]; array[i]=array[depth]; array[depth]=temp;
                            count += derange(array, LEN, display, Peano, depth+1);
                            temp=Peano[i]; Peano[i]=Peano[depth]; Peano[depth]=temp;
                            temp=array[i]; array[i]=array[depth]; array[depth]=temp;}
                    return count;}

【问题讨论】:

  • 请清理您的代码展示。分配Peano 有什么意义?您希望它是一个由 4 个(或LEN)整数组成的数组,但您只为一个整数分配存储空间。为什么不使用int Peano[LEN]

标签: c algorithm permutation


【解决方案1】:

这里:

int i ,LEN=4, *Peano=malloc(sizeof(int));

您将单个整数的空间分配给PeanoPeano 是一个与 array 并排的索引数组,长度为 4。只需将其创建为堆栈上的自动变量即可:

int Peano[4];

derange 中的循环还有另一个问题:

for (i = LEN - 1; i >= depth; i--) ...

这是一个循环 tat 向下计数有符号的 int i。但是,您的变量 depthunsigned。这意味着在比较 i &gt;= depth 中,已签名的 i 被“提升”为未登录。如果 depth 为零,则该比较将始终为真,因为 i &gt;= 0 对于每个定义的所有未签名整数都为真。

您可以通过将depth 设为int 而不是unsigned 或使用适用于有符号和无符号类型的向下循环变体来解决此问题:

for (i = LEN; i-- > depth; ) ...

或者,如果您不喜欢空的更新子句

i = LEN;
while (i-- > depth) ...

【讨论】:

  • int类型转换为无符号类型的条件是什么? unsigned 类型转换为 int 类型的条件是什么?因为 c prime plus 说“当出现在表达式中时,char 和 short,无论有符号还是无符号,都会自动转换为 int,或者,如果需要,转换为 unsigned int。”
  • 如果两个整数有相同的“rank”,但一个是无符号的,另一个是有符号的,常见的类型是该等级的无符号类型,在你的例子中是unsigned int。跨度>
  • 一般来说,您的代码存在一定的不整洁性,不仅在表现形式上,而且在逻辑上。对于不能为负数的事物(如数组大小和位置)使用无符号类型是可以的,但如果您使用无符号,则应始终使用无符号,即peano 数组及其大小。如果您使用无符号,请确保您的计数器不会低于零,因为如果是这样,它们将被视为非常大的数字。使用我在答案中显示的循环。
猜你喜欢
  • 2015-01-20
  • 2020-05-23
  • 1970-01-01
  • 2022-07-04
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-09-05
  • 1970-01-01
相关资源
最近更新 更多