C - 문자열

C 언어의 문자열은 char의 배열로 이루어진다. 그리고 배열의 끝은 '\0'(NUL)로 끝난다.

"DeneV"
{'D', 'e', 'n', 'e', 'V', '\0'}

"DeneV"라는 문자열은 "DeneV\0"로 구성되어 있기 때문에 6 Byte의 크기를 가진다. 


선언

char str[] = {'D', 'e', 'n', 'e', 'V', '\0'};
char str[] = "DeneV";

char str[5] = "DeneV";  // 주의
char str[5] = "abc";  // {'a', 'b', 'c', '\0', '\0'}

배열과 같은 방식으로 선언하거나 " "(큰 따옴표)를 활용해 선언할 수 있다. 선언된 문자열보다 배열의 크기가 클 경우, 빈 공간은 '\0'로 선언된다. 


입출력

char str[10];
scanf("%s", str);
입력: Hello World !
결과: Hello

형식문자 "%s"를 이용해 입력받을 수 있다. 문자열의 변수명은 배열의 포인터를 가르키기 때문에 '&' 없이 사용한다. 하지만 위 경우 스페이스 단위로 끊어서 불러오기 때문에 문자열을 모두 인식할 수 없다. 

char str[10];

scanf(" %[^\n]s", str);
// gets(str);
입력: Hello World !
결과: Hello World !

" %[^\n]s"와 같은 형태로 입력하면 스페이스는 하나의 문자로 인식하고, '\n'(줄바꿈)을 만나면 입력을 종료한다. 

다른 방식으로 gets 함수를 이용하면 똑같은 효과를 낼 수 있다. 

char str[] = "DeneV";
printf("%s", str);
// DeneV

char str[5] = "DeneV";
printf("s", str);
// DeneV儆儆儆儆儆儆儆儆儆儆儆鵑삇?

문자열은 "%s" 형식문자를 활용해 출력할 수 있으며, '\0' 문자까지 출력한다. 만약 '\0'으로 끝나지 않은 배열을 사용할 경우, 메모리에 있던 예상치 못한 값이 함께 출력된다. 


함수 활용

문자열은 배열이기 때문에 포인터를 활용해 배열을 넘겨준다.

#include <stdio.h>

void PrintStr(char str[]);

int main(void) 
{
	char name[] = "DeneV";
	PrintStr(name);
	// 출력: DeneV
	return 0;
}

void PrintStr(char str[])
{
	printf("출력: %s", str);
}

일반적으로 배열을 조작하기 위해 배열의 크기를 함께 인자로 넘겨주지만 문자열은 배열의 크기 없이도 '\0'의 위치를 활용해 조작할 수 있다. 

예시: 

#include <stdio.h>

void Upper(char str[]);

int main(void) 
{
	char name[] = "DeneV";
	Upper(name);
	printf("name: %s", name);
	return 0;
}

void Upper(char str[])
{
	int diff = 'a' - 'A';
	for (int i = 0; str[i] != '\0'; i++) {
		if (97 <= str[i] && str[i] <= 122) {
			str[i] = str[i] - diff;
		}
	}
}

<string.h>

string.h는 문자열을 다루기 위한 여러 함수를 제공한다. 

예시:

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

int main(void) 
{
	char str1[] = "ABC";
	char copied[10];
	
	// strlen: 문자열의 길이
	unsigned int length = strlen(str1);
	printf("strlen: %u\n", length);
	// strlen: 3

	// strcpy: 문자열 복사
	strcpy(copied, str1);
	printf("strcpy: copied -> %s\n", copied);
	// strcpy: copied -> ABC

	// strcmp: 문자열 비교
	int res = strcmp(str1, copied);
	printf("strcmp: %d\n", res);
	// strcmp: 0

	return 0;
}