4

私の課題の 1 つは、独自の UNIX シェルを作成することです。ユーザーからの入力を受け取るために、fgets を使用して入力を文字列としてキャプチャしていますが、それがどのように機能するかはよくわかりません。私が実行すると:

char command[50];
fgets(command, sizeof(command), stdin);

printf("Your Command: %s", &command);
int length = strlen(command);
printf("Length of String: %d\n", length);

私の入力が「終了」だったとしましょう。strlen は、文字列の長さが 4 文字ではなく 5 文字であることを示しています。私はこれをしたい:

if( (strcmp(command, "exit")) == 0 ){
    doSomething();
}

しかし、コマンドは私が望む文字列と決して等しくありません。よくわからない未知のキャラクターを持っているようです。最後にヌル文字ですか?if ステートメントを変更して、fgets でキャッチされたユーザー入力が「exit」に等しいことを確認するにはどうすればよいですか? ありがとう!

4

7 に答える 7

7

fgets行末記号を有効な文字と見なします。それがあなたが受け取っている追加のキャラクターです。

command[strlen(command) - 1] = '\0';行末記号を削除するようなことをしてください。その後、すべてのことを自由に行うことができますstrcmp

于 2011-02-04T01:06:50.560 に答える
4

fgetsマニュアルページから:

fgets() は、stream から最大で size 未満の 1 文字を読み取り、s が指すバッファーに格納します。EOF または改行の後、読み取りは停止します。 改行が読み取られると、バッファに格納されます。 '\0' は、バッファー内の最後の文字の後に格納されます。

結論: 比較すると、文字列の最後に余分な改行があります。

于 2011-02-04T01:08:23.530 に答える
3

fgets入力文字列には常に行末文字が含まれます。次のようにして、「コマンド」の末尾から改行文字を含むスペースを削除できます。

char command[50];
fgets(command, sizeof(command), stdin);

size_t length = strlen(command);
// Trim off trailing "spaces" including newline characters
while ((length > 0) && isspace(command[length-1]))
      command[--length] = '\0';

printf("Your Command: %s\n", &command); // Include newline now...
// This is computed above...
// int length = strlen(command);

// Continue as before
于 2011-02-04T01:13:08.060 に答える
2

scanfおそらく、これを処理する最も簡単な方法は、入力を読み取るために using に切り替えることです。

char command[51];

scanf("%50[^\n]", command);

if (0 == strcmp(command, "exit"))
    do_something();
于 2011-02-04T01:38:08.677 に答える
2

fgetsも改行をキャプチャしています。

これをいくつかの方法で克服できることに注意してくださいstrncmp

if((strncmp(command, "exit", 4)) == 0)

これは、コマンドの最初の 4 文字だけが一致するかどうかをチェックします (ただし、これは適切なオプションではない可能性があります)。

もう 1 つの戦術は、改行を適切にチェックすることです。

if((strcmp(command, "exit\n")) == 0)
于 2011-02-04T01:07:32.667 に答える
1

文字列の最後にはまだ改行があります。のようなものと比較し"exit\n"たり、使用したりできstrncmp(command, "exit", 4)ます。「exit」で始まるものはすべて受け入れ、残りは無視することに注意してください。

于 2011-02-04T01:08:15.857 に答える
0

前述のように、fgets(3) は末尾に '\n' を付けます。(3)を使用するgetsと、末尾の改行が取得されません。一貫性のようなものはありません。

Perl には、末尾の改行がある場合はそれを削除する手動の chomp() 関数があります。

#define NUL ((char)0)
void chomp( char *s )
{
  if ( s != null )
  {
    int len = strlen(s) ;
    if ( len >= 1 && s[len-1] == "\n" )
    {
      s[len-1] = NUL ;
    }
  }
  return ;
}
于 2011-02-04T01:21:43.913 に答える