[c] 문자열을 올바르게 비교하려면 어떻게합니까?

사용자가 단어 나 문자를 입력하고 저장 한 다음 사용자가 다시 입력 할 때까지 인쇄하여 프로그램을 종료 할 수있는 프로그램을 얻으려고합니다. 내 코드는 다음과 같습니다

#include <stdio.h>

int main()
{
    char input[40];
    char check[40];
    int i=0;
    printf("Hello!\nPlease enter a word or character:\n");
    gets(input);
    printf("I will now repeat this until you type it back to me.\n");

    while (check != input)
    {
        printf("%s\n", input);
        gets(check);
    }

    printf("Good bye!");


    return 0;
}

문제는 사용자의 입력 (확인)이 원본 (입력)과 일치하더라도 입력 문자열을 계속 인쇄한다는 것입니다. 두 가지를 잘못 비교하고 있습니까?



답변

당신은 (유용)를 사용하여 문자열을 비교할 수 없습니다 !=또는 ==사용할 필요가 strcmp:

while (strcmp(check,input) != 0)

때문에 그 이유는 !=하고 ==만 문자열의 기본 주소를 비교합니다. 문자열 자체의 내용이 아닙니다.


답변

몇 가지 확인 : gets안전fgets(input, sizeof(input), stdin) 하지 않으며 버퍼 오버플로가 발생하지 않도록 대체해야합니다 .

다음으로 문자열을 비교하려면을 사용해야합니다 strcmp. 여기서 반환 값 0은 두 문자열이 일치 함을 나타냅니다. 항등 연산자 (즉, !=)를 사용하면 두 문자열의 주소가 char내부 의 개별 문자열과 비교되는 것과 비교 됩니다.

또한이 예제에서는 문제를 일으키지 않지만 fgets개행 문자를 '\n'버퍼에도 저장합니다 . gets()하지 않습니다. 사용자 입력을 fgets()문자열 리터럴과 비교하면 "abc"결코 일치하지 않을 것입니다 (버퍼가 너무 작아서 '\n'맞지 않을 경우).


답변

사용하십시오 strcmp.

이것은 string.h도서관에 있으며 매우 인기가 있습니다. strcmp문자열이 같으면 0을 반환합니다. 무엇이 반환 되는지에 대한 자세한 설명은 이것을 참조하십시오 strcmp.

기본적으로 다음을 수행해야합니다.

while (strcmp(check,input) != 0)

또는

while (!strcmp(check,input))

또는

while (strcmp(check,input))

확인할 수 있습니다 ,에 대한 자습서를 strcmp.


답변

이처럼 직접 배열을 비교할 수 없습니다

array1==array2

당신은 그것들을 문자별로 비교해야합니다; 이를 위해 함수를 사용하고 부울 (True : 1, False : 0) 값을 반환 할 수 있습니다. 그런 다음 while 루프의 테스트 조건에서 사용할 수 있습니다.

이 시도:

#include <stdio.h>
int checker(char input[],char check[]);
int main()
{
    char input[40];
    char check[40];
    int i=0;
    printf("Hello!\nPlease enter a word or character:\n");
    scanf("%s",input);
    printf("I will now repeat this until you type it back to me.\n");
    scanf("%s",check);

    while (!checker(input,check))
    {
        printf("%s\n", input);
        scanf("%s",check);
    }

    printf("Good bye!");

    return 0;
}

int checker(char input[],char check[])
{
    int i,result=1;
    for(i=0; input[i]!='\0' || check[i]!='\0'; i++) {
        if(input[i] != check[i]) {
            result=0;
            break;
        }
    }
    return result;
}


답변

포인터 의 개념에 오신 것을 환영합니다 . 여러 세대의 초보 프로그래머가이 개념을 이해하기 어려웠지만 유능한 프로그래머로 성장하려면 결국이 개념을 숙달해야합니다. 또한 이미 올바른 질문을하고 있습니다. 잘 됐네요

주소가 무엇입니까? 이 다이어그램을보십시오 :

----------     ----------
| 0x4000 |     | 0x4004 |
|    1   |     |    7   |
----------     ----------

다이어그램에서 정수 1은 주소 0x4000의 메모리에 저장됩니다 . 왜 주소에? 도시가 크고 많은 가족을 수용 할 수있는 것처럼 메모리가 크고 많은 정수를 저장할 수 있기 때문에. 각 정수는 집에 상주하므로 각 정수는 메모리 위치에 저장됩니다. 각 집은 주소 로 식별되므로 각 메모리 위치는 주소 로 식별됩니다.

다이어그램의 두 상자는 서로 다른 두 개의 메모리 위치를 나타냅니다. 마치 마치 집처럼 생각할 수 있습니다. 정수 1은 주소 0x4000 ( “4000 Elm St.”)의 메모리 위치에 있습니다. 정수 7은 주소 0x4004 ( “4004 Elm St.”)의 메모리 위치에 있습니다.

프로그램이 1과 7을 비교한다고 생각했지만 그렇지 않았습니다. 0x4000과 0x4004를 비교하고있었습니다. 이 상황이 발생하면 어떻게됩니까?

----------     ----------
| 0x4000 |     | 0x4004 |
|    1   |     |    1   |
----------     ----------

두 정수는 동일하지만 주소가 다릅니다. 프로그램이 주소를 비교합니다.


답변

문자열을 비교하려고 할 때마다 각 문자와 관련하여 문자열을 비교하십시오. 이를 위해 strcmp (input1, input2)라는 내장 문자열 함수를 사용할 수 있습니다. 그리고 당신은라는 헤더 파일을 사용해야합니다#include<string.h>

이 코드를 사용해보십시오 :

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

int main()
{
    char s[]="STACKOVERFLOW";
    char s1[200];
    printf("Enter the string to be checked\n");//enter the input string
    scanf("%s",s1);
    if(strcmp(s,s1)==0)//compare both the strings  
    {
        printf("Both the Strings match\n");
    }
    else
    {
        printf("Entered String does not match\n");
    }
    system("pause");
} 


답변

문자열을 올바르게 비교하려면 어떻게합니까?

char input[40];
char check[40];
strcpy(input, "Hello"); // input assigned somehow
strcpy(check, "Hello"); // check assigned somehow

// insufficient
while (check != input)

// good
while (strcmp(check, input) != 0)
// or 
while (strcmp(check, input))

check != input충분하지 않은지 더 깊이 파헤쳐 보자 .

C에서 문자열 은 표준 라이브러리 사양입니다.

문자열은 첫 번째 널 문자를 포함 연속에 의해 종료 문자의 순서와입니다.
C11 §7.1.1 1

input위의 문자열 이 아닙니다 . input문자의 어레이 (40) .

의 내용은 문자열input 이 될 수 있습니다 .

대부분의 경우 배열을 식에 사용하면 첫 번째 요소의 주소로 변환됩니다.

아래는 첫 번째 요소의 각 주소 로 변환 check되고 input해당 주소가 비교됩니다.

check != input   // Compare addresses, not the contents of what addresses reference

문자열 을 비교하려면 해당 주소를 사용하고 그들이 가리키는 데이터를 확인해야합니다.
strcmp()일을한다 . §7.23.4.2

int strcmp(const char *s1, const char *s2);

strcmp기능이 가리키는 문자열을 비교 s1문자열에 의해 지적에 s2.

strcmp함수는 by s1가 가리키는 문자열이 by 가 가리키는 문자열보다 크거나 같거나 작으므로 정수보다 크거나 같거나 0보다 작은 정수를 반환합니다 s2.

코드가 문자열이 동일한 데이터인지 여부를 찾을 수있을뿐만 아니라 문자열이 다르면 더 큰지 아닌지를 찾을 수 있습니다.

문자열이 다를 경우 다음과 같습니다.

strcmp(check, input) != 0

통찰력을 얻으려면 함수 만들기를 참조하십시오.strcmp()