C错误的变量递减

时间:2015-05-08 15:32:08

标签: c for-loop

所以我现在非常困惑。在下面的代码中,我初始化一个for循环并尝试递减size_t变量。但是,在执行此操作时,似乎另一个size_t变量开始递减。

代码如下:

/**
 * sanitize_octet - Sanitizes a given octet for ipv4 calculation
 * requirements.
 *
 * @octet - Octet to be sanitized.
 *
 * returns:
 * NULL pointer - failure
 * Pointer to ret - success
 */
const char *sanitize_octet(const void *octet)
{
        char ret[4];
        size_t i = strlen(octet), j = i;

        if(i > 3) {
                printf("error: '%s' is not a valid octet.", (char *) octet);
                return NULL;
        }
        strcpy(ret, (char *) octet);
        while(i--) {
                if(!isdigit(ret[i])) {
                        printf("error: '%s' is not a valid octet.", ret);
                        return NULL;
                }
                if((int) ret[i] > 255) {
                        printf("error: '%s' is not a valid octet.", ret);
                        return NULL;
                }
        }
        if(j != 3) {
                i = 3 - j;
                for(j = 2; j > 1; j--) {
                        printf("j: %d, i: %d\n", j, i);
                        system("pause");
                }
        }
        puts(ret);
}

该功能仍在进行中。让我感到困惑的是底部的for loop。当初始化为for(j = 2; j > 1; j--时,它实际上会递减i而不是j,并且只会执行直到崩溃为止。但是,如果我用j初始化具有不同值(例如3)的循环,它将按预期执行。我之前从未见过这样的事情而且非常困惑。

以下是j初始化为2的示例控制台输出:

j: 2, i: 2
Press any key to continue . . .
1




j: 2, i: 1
Press any key to continue . . .
19

您可以清楚地看到i正在递减,而不是j

可能导致这种情况的原因是什么?

更新:这是导致无限循环的代码:

const char *sanitize_octet(const void *octet)
{
        char ret[4];
        size_t i = strlen(octet), j = i;

        if(i > 3) {
                printf("error: '%s' is not a valid octet.", (char *) octet);
                return NULL;
        }
        strcpy(ret, (char *) octet);
        while(i--) {
                if(!isdigit(ret[i])) {
                        printf("error: '%s' is not a valid octet.", ret);
                        return NULL;
                }
                if((int) ret[i] > 255) {
                        printf("error: '%s' is not a valid octet.", ret);
                        return NULL;
                }
        }
        if(j != 3) {
                i = 3 - j;
                for(j = 2; j >= 0; j--) {
                        if(i) {
                                i--;
                        }
                        printf("j: %d, i: %d\n", j, i);
                        system("pause");
                }
        }
        puts(ret);
}

以下是该确切代码的控制台输出:

j: 2, i: 1
Press any key to continue . . .
j: 1, i: 0
Press any key to continue . . .
j: 0, i: 0
Press any key to continue . . .
j: -1, i: 0
Press any key to continue . . .
j: -2, i: 0
Press any key to continue . . .
j: -3, i: 0
Press any key to continue . . .
j: -4, i: 0
Press any key to continue . . .
j: -5, i: 0
Press any key to continue . . .
j: -6, i: 0
Press any key to continue . . .
j: -7, i: 0
Press any key to continue . . .
j: -8, i: 0
Press any key to continue . . .
j: -9, i: 0
Press any key to continue . . .

3 个答案:

答案 0 :(得分:3)

回答问题的第一个版本:

您的输出清楚地显示您调用sanitize_octet一次,获得输出

  

j:2,i:2
  按任意键继续 。 。 。
  1

然后使用不同的参数再次调用sanitize_octet,然后获取输出

  

j:2,i:1
  按任意键继续 。 。 。
  19

你的循环体在你对sanitize_octet的两次调用中只执行一次,因此j和i都没有递减。

回答你问题的第二个版本:

jsize_t,是无符号值。所以j>=0总是如此 您的printf只是模糊不清,因为它将size_t视为已签名的int并将其打印为j,并将其声明为int

答案 1 :(得分:2)

@ user3121023的评论是现货。

让我们将代码简化为:

int j;
for (j = 2; j > 1; j--) {
    printf("j = %d\n", j);
}

你会看到类似的结果... j = 2输出行,然后再没有了。

现在让我们分解代码以删除for循环并将其替换为goto(出于说明的原因)。这是最终结果:

    j = 2;
loop:
    printf("j = %d\n", j);
    j--;
    if (j > 1) goto loop;

这种分解很明显,为什么你只得到一行输出,因为循环终止时j递减到1,导致if条件失败。

答案 2 :(得分:0)

size_t未签名。因此,虽然printf用符号打印,但j总是> = 0.您必须更改类型。