프로그래밍 언어/C

[문자와 문자열] 입출력 함수 총정리 2 : 문자열

순정법사 2023.08.17

C. 문자열

1. 문자열(string)

a. 문자열 상수(string constant)

큰따옴표("")를 사용해 표현되는 문자열을 문자열 상수(string constant)라고 함

이름이 없고, 내용을 변경할 수 없어서 상수라고 표현함

 

b. 문자열

🌟 메모리에 저장된 일련의 연속된 문자(character)들의 집합

 

👉 문자형 배열로 표현, 이 배열이 곧 문자열 변수가 됨

💥 문자형 배열이기 때문에 기본 타입에 포함되지 않음 = 연산자 사용 불가능

 

🤓 예제 : 문자열 상수 및 변수를 선언하는 여러 방법

char str01[] = "This is a string.";    // 크기를 지정하지 않은 문자열 변수 선언
char str02[7] = "string";              // 크기를 지정한 문자열 변수 선언

printf("이것은 문자열 상수입니다.\n"); // 문자열 상수
printf("문자열 str01에 저장되어 있는 문자열은 \"%s\"입니다.\n", str01);
printf("문자열 str02에 저장되어 있는 문자열은 \"%s\"입니다.\n", str02);

✨ 실행결과

이것은 문자열 상수입니다.

문자열 str01에 저장되어 있는 문자열은 "This is a string."입니다.

문자열 str02에 저장되어 있는 문자열은 "string"입니다.

 

c. NULL 문자

문자형 배열로 선언된 문자열 변수는 문자열의 끝을 프로그램에 따로 알려줘야 함

그래야 실제 문자열에 속한 값과 그 외 쓰레기값을 구분할 수 있음

 

따라서 문자열에 속한 데이터가 끝나면, 문자열의 끝을 의미하는 문자(NULL)를 하나 더 삽입함

'\0'으로 표시, 아스키코드값은 0

 

🤓 예제 : 널 문자를 제외한 문자열의 길이를 계산하여 출력

int str_len = 0;
char str[] = "string";

while (str[str_len] != '\0') // 널 문자가 나올 때까지 길이를 증가함
{
    str_len++;
}

printf("이 문자열의 길이는 %d입니다.\n", str_len);

✨ 실행결과

이것은 문자열 상수입니다.
문자열 str01에 저장되어 있는 문자열은 "This is a string."입니다.
문자열 str02에 저장되어 있는 문자열은 "string"입니다.

 

🎨 도식화

 

 

 

 

 

D. 문자열 입출력 함수

1. 문자열 입력 함수

a. fgets()

🌟 키보드뿐만 아니라 파일에서도 문자열을 입력받을 수 있는 함수

 

📘 원형

#include <stdio.h>

char *fgets(char * restrict s, int n, FILE * restrict stream);

첫 번째 인수 : 입력받는 문자열을 저장하기 위해 선언한 배열의 시작 주소
두 번째 인수 : 입력 받을 수 있는 문자열의 최대 길이
세 번째 인수 : 문자열을 입력받을 스트림

 

 

2. 문자열 출력 함수

a. puts()

🌟 표준 출력 스트림(stdout)인 모니터에 하나의 문자열을 출력하는 함수

 

모니터에 문자열을 출력한 다음 줄바꿈

 

📘 원형

#include <stdio.h>

int puts(const char *s);  

인수 : 출력할 문자열을 가리키는 포인터를 전달

 

b. fputs()

🌟 모니터뿐만 아니라 파일을 통해서도 문자를 출력(저장)할 수 있는 함수

 

문자 출력 후 줄바꿈

 

📘 원형

#include <stdio.h>

int fputs(const char * restrict s, FILE * restrict stream);

첫 번째 인수 : 출력할 문자열을 가리키는 포인터를 전달
두 번째 인수 : 문자열을 출력할 스트림을 전달

 

🤓 예제 : 입력한 문자열을 그대로 출력

#include <stdio.h>

int main(void)
{
    char str[100];

    fputs("문자열을 입력해 주세요 :\n", stdout);
    fgets(str, sizeof(str), stdin);
    puts("입력하신 문자열 : ");
    puts(str);	//자동줄바꿈
    fputs("입력하신 문자열 : ", stdout);
    fputs(str, stdout);
    return 0;
}

✨ 실행결과

문자열을 입력해 주세요 :
C언어 문자열 입출력
입력하신 문자열 : 
C언어 문자열 입출력

입력하신 문자열 : C언어 문자열 입출력

 

 

 


E. 문자열 처리 함수 

1. 문자열 처리 함수

문자열은 문자형 배열 즉, 기본 타입이 아니기 때문에 함수를 이용해서 문자열 처리를 해야 함

 

a. strlen() 

🌟  인수로 전달된 문자열의 길이를 반환하는 함수

 

👉  문자열 여부를 구분하는 마지막 문자인 널 문자는 문자열의 길이에서 제외

 

📘 원형

#include <string.h>

size_t strlen(const char *s);

 

🤓 예제 : 문자열의 길이를 구하기

char str[] = "C언어";  

printf("이 문자열의 길이는 %d입니다.\n", strlen(str));

✨ 실행결과

이 문자열의 길이는 7입니다.

 

👉 utf-8 인코딩 환경에서 한글은 한 문자당 3바이트로 처리

 

b. strcat(), strncat() 

🌟  하나의 문자열에 다른 문자열을 연결해주는 함수 (string concatenation)

 

💥 strcat()은 기준 문자열이 저장된 배열의 공간이 충분하지 않으면 남은 문자들이 흐르는 overflow가 발생

따라서 strncat()함수를 사용해야 함

👉 strncat()함수는 널 문자를 만나거나, 추가하는 문자의 개수가 세 번째 인수 길이에 도달할 때까지 추가

 

📘 원형

#include <string.h>

char *strncat(char * restrict s1, const char * restrict s2, size_t n);  

첫 번째 인수 : 기준 문자열
두 번째 인수 : 추가하고자 하는 문자열의 복사본이 기준 문자열 뒤에 추가
세 번째 인수 : 추가할 문자열의 최대 길이를 지정

 

💙 restrict 키워드

포인터의 선언에서만 사용할 수 있는 C99부터 추가된 키워드
포인터를 선언할 때 이 키워드를 명시하면, 컴파일러는 해당 포인터가 가리키는 메모리에 대한 최적화를 실시

 

🎨 도식화

 

 

🤓 예제

char str01[20] = "C language is "; // 널 문자를 포함하여 15문자
char str02[] = "Cool! and funny!";  

//strcat(str01, str02);   // 이 부분의 주석 처리를 삭제한 후 실행시키면 배열 오버플로우가 발생함
strncat(str01, str02, 5); // 이렇게 최대 허용치를 설정해 놓으면 배열 오버플로우에 대해서는 안전해짐

puts(str01);

✨ 실행결과

C language is Cool!

 

c. strcpy(), strncpy() 

🌟  첫 번째 인수로 전달된 배열에, 두 번째 인수로 전달된 문자열을 복사하는 함수

 

💥 strcpy()은 첫 번째 인수로 전달된 배열의 크기가 복사할 문자열의 길이보다 작으면, 배열 오버플로우가 발생

👉 strncpy()함수는 널 문자를 만나거나, 추가하는 문자의 개수가 세 번째 인수 길이에 도달할 때까지 추가

 

📘 원형

#include <string.h>

char *strncpy(char * restrict s1, const char * restrict s2, size_t n);

 

🎨 도식화

 

 

🤓 예제 1 : 문자열의 일부분만을 복사

char str01[20] = "C is Cool!";
char str02[11];  

// str02 배열의 크기만큼만 복사를 진행하며, 마지막 한 문자는 널 문자를 위한 것임
strncpy(str02, str01, sizeof(str02)-1);
str02[sizeof(str02)-1] = '\0'; // 이 부분을 주석 처리하면, 맨 마지막에 널 문자를 삽입하지 않음
puts(str02);

✨ 실행결과

C is Cool!

 

👉 복사한 문자열의 마지막에는 반드시 널 문자를 삽입해 주어야만 C 프로그램이 제대로 문자열로 인식

 

🤓 예제 2 : 문자열의 일부분만을 수정

char str[20] = "C is cool!";  

strncpy(str+5, "nice", 4); // 배열 이름을 이용한 포인터 연산으로 수정할 부분의 시작 부분을 지정함

puts(str);

✨ 실행결과

C is Cool!

 

👉 첫 번째 인수에 배열 이름을 이용한 포인터 연산을 사용하여 수정을 시작할 지점을 지정

 

d. strcmp(), strncmp()

🌟  두 개의 문자열 포인터를 전달받아 문자열의 내용을 비교하는 함수

 

모든 문자는 아스키 코드값으로 자동 변환

문자열의 맨 앞에서부터 순서대로 비교

⦁ 문자열을 비교하는 함수이므로, 문자를 비교할 때에는 관계연산자 '=='를 사용

 

📘 원형

#include <string.h>

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

int strncmp(const char *s1, const char *s2, size_t n);

 

👉 둘이 하는일은 같고, 단지 세번째 인수를 가지고 있는지 없는지만 다르다

일치하지 않는 문자를 만나거나, 세 번째 인수로 전달된 문자의 개수만큼 비교를 계속함

 

📊 strcmp() 함수의 상황별 반환값

 반환값 설명
양수 첫 번째 인수로 전달된 문자열이 더 큰 경우
0 두 문자열의 내용이 완전히 같은 경우
음수 두 번째 인수로 전달된 문자열이 더 큰 경우임.

 

🤓 예제 : 문자열 내의 모든 영문자를 대문자로 변환

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

int main(void)
{
    char str[20];
    char ch;   

    while (1)
    {
        puts("미국의 수도를 입력하세요 :");
        scanf("%s", str);
        if (strcmp(str, "워싱턴") == 0 || strcmp(str, "washington") == 0) // 문자열의 비교
        {
            puts("정답입니다!");
            break;
        }

        else
            puts("아쉽네요~");
        fflush(stdin);   

        puts("\n이 프로그램을 끝내고자 한다면 'q'를 눌러주세요!");
        puts("계속 도전하고자 하시면 Enter를 눌러주세요!");
        scanf("%c", &ch);  

        if (ch == 'q') // 문자의 비교
        {
            break;
        }

        fflush(stdin);
    }

    return 0;
}

✨ 실행결과

미국의 수도를 입력하세요 :

뉴욕

아쉽네요~



이 프로그램을 끝내고자 한다면 'q'를 눌러주세요!

계속 도전하고자 하시면 Enter를 눌러주세요!



미국의 수도를 입력하세요 : 

워싱턴

정답입니다!

 

e. atoi(), atol(), atoll(), atof()

🌟  인수로 전달된 문자열을 해당 타입의 숫자로 변환시켜주는 함수

 

📘 원형

#include <stdlib.h>

int atoi(const char *nptr);            // int형 정수로 변환함.
long int atol(const char *nptr);       // long형 정수로 변환함.
long long int atoll(const char *nptr); // long long형 정수로 변환함.
double atof(const char *nptr);         // double형 실수로 변환함.

 

🤓 예제 : 숫자로 이루어진 문자열을 숫자로 변환하여, 곱셈 연산을 수행

char str01[] = "10";
char str02[] = "20";  

printf("문자열을 숫자로 변환해서 곱한 값은 %d입니다.\n", atoi(str01) * atoi(str02));

✨ 실행결과

문자열을 숫자로 변환해서 곱한 값은 200입니다.

 

f. toupper(), tolower() 

🌟  인수로 전달된 문자열의 영문자를 모두 대문자나 소문자로 변환시켜주는 함수

 

📘 원형

#include <ctype.h>

int toupper(int c); // 문자열의 모든 영문자를 대문자로 변환함.

int tolower(int c); // 문자열의 모든 영문자를 소문자로 변환함.

 

🤓 예제 : 문자열 내의 모든 영문자를 대문자로 변환

int i, str_len;
char str[] = "Hello C World!";  
printf("원래 문자열 : %s\n", str);

str_len = strlen(str);

for (i = 0; i < str_len; i++)
{
    str[i] = toupper(str[i]);
}

printf("바뀐 문자열 : %s\n", str);

✨ 실행결과

원래 문자열 : Hello C World!
바뀐 문자열 : HELLO C WORLD!

 

 

 


출처 : http://www.tcpschool.com/c/c_string_string

 

코딩교육 티씨피스쿨

4차산업혁명, 코딩교육, 소프트웨어교육, 코딩기초, SW코딩, 기초코딩부터 자바 파이썬 등

tcpschool.com