web-dev-qa-db-ja.com

引数として文字配列を渡します

私がここで理解できないことを誰かに説明してもらえますか?

引数を「文字列」として渡そうとしているので(cには文字列がないことがわかります)、その文字列を後で渡されるファイル名などの他の関数で使用できるようにします。しかし、それがなぜそれを受け入れないのか、それがどのようなタイプであるべきなのかはわかりません

#include <stdio.h>

int main ( int argc, char *argv[] )
{
    char *array= argv[0];
    foo(*array);
}

void foo( char *array) 
// notice the return type - it's a pointer
{
    printf(array);
}

どうもありがとう!

8
Ryan

次のような関数を呼び出す必要があります。

foo(array);

文字列の最初の文字であるcharを返すポインターを逆参照しています。

printfの呼び出しも次のようになります。

printf("%s", array);

修正したコード全体は次のようになります。

#include <stdio.h>

void foo(char *array)
{
    printf("%s", array);
}

int main ( int argc, char *argv[] )
{
    // TODO:  make sure argv[1] exists
    char *array= argv[1];
    foo(array);
}
17
Tim Cooper

foo (*array)と言うと、その要素を逆参照して最初の文字を取得するために、配列を最初の要素へのポインターに分解しています。それが関数に渡そうとしていることです。アスタリスクを省略してarrayを渡すだけで、必要なポインターに減衰します。

もう1つの問題は、printfを正しく使用していないことです。まず、ここに 参照 を示します。トークンの文字列を渡す必要があります。トークンの文字列を渡すには、コンパイラーに次に期待する引数のタイプを指示する方法がないためです。あなたの場合、文字列には"%s"が含まれることを伝えるためにchar *が含まれ、arrayをそのchar *引数として渡します。

printf ("The string is %s", array);
5
chris

argvは文字ポインターの配列です。つまり、argvは、コマンドライン引数として渡したすべての文字列のアドレスを格納します。

したがって、_argv[0]_は、コマンドライン引数として渡した最初の文字列のアドレスを提供します。これは、array関数のポインター変数mainに格納します。

これで、アドレスのみを関数fooに渡す必要がありますが、その文字列の最初の文字を渡しています。たとえば、最初のコマンドライン引数が_temp.txt_の場合、関数tに文字fooを渡します。つまり、foo関数の内部には、charポインタ変数arrayがあり、そのASCII文字tの値が割り当てられます。そして次に、それをprintfに渡します。これにより、ASCIIの値がアドレスとして読み込まれ、そのアドレスにアクセスして印刷が行われ、クラッシュにつながります(予期しない動作)。 。

したがって、以下のように、コマンドライン引数のアドレスのみを関数fooに渡す必要があります。

foo(array);

printf(array)-ここでprintfはフォーマット指定子をstring(_%s_)として読み取り、アドレスarrayから始まるすべての文字を出力しますヌル文字_\0_を満たしています。

ただし、以下のようにprintfを追加することをお勧めします

printf("%s", array);

1
rashok