0

このコードを理解するのに少し苦労しています。なぜ長さは3ですか?を入力するhiと、長さは 1 です。

#include <stdlib.h>
#include <stdio.h>

int len(char *s)  
{
    int i = 0; 
    while(*(++s) != '\0') 
        i++; 
    printf("%d", i);
    return i; 
} 

int main()
{
    len("this");
    getchar();
}
4

4 に答える 4

1

長さが 1 ずれるだけでなく、0 を返したいところに空の文字列を引数として指定すると、アクセス違反になる可能性があります (ただし、ほとんどの場合はゼロなのでそうはなりません)。バイトは初期化されていないメモリでは非常に一般的です)、または乱数 (基本的に、c-string の空の文字列定数の 1 バイト後ろに格納されているゼロ以外のバイト数を返します。

行の最初のものとして評価されるプレフィックスインクリメンタル演算子を使用しているため、長さは 1 ずれています。

while(*(++s)!='\0') 

具体的には、そこで何をしているのかを長い目で見ると、次のようになります。

char *s = "this";
int i = 0;

while (1) {
    s = s + 1;
    if (*s == '\0') break;
    i++;
}
printf("%d", i);
...

問題が見えますか? ++s最初にポインタをインクリメントします。したがって、文字列の最初の文字をスキップします。

とにかく、おそらくあなたが望むのは次のようなものです:

int len(const char *s) {

    int clen = 0;
    while (*s++ != '\0') clen++;
    return clen;

}

もちろん、標準 C ライブラリを持っstrlen()ているのに、なぜ車輪を再発明するのかと尋ねる人もいるかもしれません。strnlen()もしかして、ただの練習?

于 2013-02-14T06:26:21.063 に答える
0

++s評価する前に値をインクリメントします。そのため、答えは実際の長さよりも 1 少なくなります。を使用しs++ます。

于 2013-02-14T06:08:40.820 に答える
0

++sは接頭辞の増分であるため、ループは実際には 2 番目の文字から開始されます。最短の修正は、後置インクリメントに変更することです:

while(*(s++) != '\0')

または:

while(*s++)
于 2013-02-14T06:09:04.710 に答える
0

質問を数回読んだ後、「len」の関数が長さ2の文字列に対して1を返すことを理解しました(「hi」など)

これは、次の行が原因です。while (*(++s)!='\0')

条件を分析すると、次のステートメントが得られます(コードに何が起こるかを明確にするためです。もちろん、これはどのように行うべきではありません)

startover: 
    s = s + 1;
    if (*s != '\0') goto end;
        i = i + 1;
    goto startover;

ご覧のとおり、カウントを開始する前に常に最初の文字をステップオーバーします。s++代わりに使用してこれを回避できます。これにより、'\0' のチェック後に s の変更が移動されます。

startover: 
    if (*s != '\0') goto end;
        s = s + 1;
        i = i + 1;
    goto startover;
于 2013-02-14T06:12:31.903 に答える