strcmp на строке, читаемой с помощью fgets
Я пытаюсь сравнить две строки. Один хранится в файле, другой извлекается из пользователя (stdin).
вот пример программы:
int main()
{
char targetName[50];
fgets(targetName,50,stdin);
char aName[] = "bob";
printf("%d",strcmp(aName,targetName));
return 0;
}
В этой программе, strcmp
возвращает значение -1, когда вход "bob"
.
Почему так? Я думал, они должны быть равны. Как я могу сделать так, чтобы они были?
6 ответов
strcmp
является одной из немногих функций, которая имеет обратные результаты true и false...если строки равны, результат равен 0, а не 1, Как вы думаете....
if (strcmp(a, b)) {
/* Do something here as the strings are not equal */
} else {
/* Strings are equal */
}
говоря о fgets
, существует вероятность того, что к концу строки прикреплена новая строка...вам нужно избавиться от него...
+-+-+-+--+--+
|b|o|b|\n||
+-+-+-+--+--+
чтобы избавиться от newline сделать это. Предостережения: не используйте "strlen (aName) - 1", поскольку строка, возвращаемая fgets, может начинаться с символа NUL - таким образом, индекс в буфере становится 1:
aName[strcspn(aName, "\n")] = '';
+-+-+-+--+
|b|o|b||
+-+-+-+--+
теперь strcmp
должна возвращать 0...
fgets
читает, пока не увидит новую строку, затем возвращается, поэтому при вводе bob в консоли targetName
содержит "bob\n", который не соответствует"bob".
Из документации fgets: (выделено жирным шрифтом)
считывает символы из потока и сохраняет их в виде строки C в str, пока (num-1) символы не будут прочитаны или либо новая строка, либо конец файла не будет достигнут, в зависимости от того, что наступит раньше. символ новой строки останавливает чтение fgets, но считается допустимым символ, и поэтому он включен в строку, скопированную в str. Нулевой символ автоматически добавляется в str после того, как символы считываются, чтобы сигнализировать конец строки C.
перед сравнением необходимо удалить новую строку из конца targetName.
int cch = strlen(targetName);
if (cch > 1 && targetName[cch-1] == '\n')
targetName[cch-1] = '';
или добавьте новую строку в тестовую строку.
char targetName[50];
fgets(targetName,50,stdin);
char aName[] = "bob\n";
printf("%d",strcmp(aName,targetName));
потому что fgets-это embededing символ новой строки в переменную targetName
. Это отбрасывает сравнение.
fgets добавляет \n
к строке, которую вы вытаскиваете из пользователя, когда они нажимают Enter. Вы можете обойти это, используя strcspn
или просто добавить \n
на конец строки, которую вы пытаетесь сравнить.
printf("Please enter put FILE_NAME (foo1, 2, or 3), ls, or exit: \n");
fgets(temp, 8, stdin);
temp[strcspn(temp, "\n")] = '';
if(strcmp(temp, "ls") == 0 || strcmp(temp, "exit") == 0)
это просто заменяет \n
С , а если вы хотите быть ленивым, вы можете просто сделать это:
printf("Please enter put FILE_NAME (foo1, 2, or 3), ls, or exit: \n");
fgets(temp, 8, stdin);
if(strcmp(temp, "ls\n") == 0 || strcmp(temp, "exit\n") == 0)
но это не так элегантно.