Home CPP Module 01 : 클래스
Post
Cancel

CPP Module 01 : 클래스

주제

  • 메모리 할당
  • 멤버 함수 포인터
  • 참조자
  • switch문

Ex00

주요 개념

  • 객체 생성 방식
  • 동적 할당

객체 생성 방식의 차이

  • newzombie
    • 동적할당 사용
    • heap 영역
    • 이유 : 객체를 생성하고 계속 사용할 것이기 때문
  • randomchump
    • 일반적인 방식 사용
    • stack 영역
    • 이유 : 객체를 생성하고 바로 소멸할 것이기 때문

Ex01

주요 개념

  • 객체를 배열로 동적할당하기 위해서는 디폴트 생성자가 존재해야한다.
  • name 변수 설정
    • 해당 변수는 private이므로 setter 함수가 필요
  • stringstream
    • 문자열을 조작할 수 있는 스트림 클래스
    • 인스턴스명.str("")와 같이 사용하여 스트림을 초기화 할 수 있다.

Ex02

주요 개념

참조자 (Reference)

  • 특정 변수의 실제 이름 대신 사용할 수 있는 별명
  • 별도의 메모리 공간을 갖지 않는다.
  • 정의 시에 반드시 누구의 레퍼런스인지를 명시해야 한다.

Ex03

  • 함수명 뒤에 const 의미 (ex. void getVariable() const;)
    • 해당 함수가 객체의 상태를 변경하지 않는다는 것을 보장
    • const 객체만 해당 함수를 호출할 수 있다.
      • const 객체는 non-const 함수를 호출할 수도 있다.
  • 참조자로 선언한 멤버 변수는 선언과 동시에 초기화를 해주어야 함.
    • 초기화 리스트 사용
  • HumanA와 HumanB에서 weapon 선언 방식의 차이
    • humanA : 생성할 때 weapon을 받음 (참조자)
    • humanB : 생성할 때 weapon을 받지 못함. (포인터)
      • NULL로 초기화.
      • attack 함수 구현시 고려 필요.
    • 참조자 타입의 변수는 생성할때 초기화를 해주어야 하기 때문에 B에게는 부적합함.
  • const를 리턴하는 함수 내에서 non-const 변수를 return 하면 const로 변환되어 리턴될까?
    • non-const 변수가 그대로 return된다.
  • 포인터를 리턴하는 함수는 *를 반환형, 함수명 중에 어느쪽에 붙여야 할까?
    • 어느 쪽에 붙이던 상관 없다.
    • char *str : C에서 일반적인 방식
    • char* str : C++에서 일반적인 방식
  • settype 매개변수에 const를 사용하는 이유?
    • 함수 내에서 인자의 값을 변경하지 않기 위해 일반적으로 const형의 매개변수를 받는다.

Ex04

주요 개념

std::ifstream

  • input file stream
  • 객체 생성 이후, open 멤버함수로 파일을 열거나 객체 생성시에 인자로 파일명을 넘겨줄 수도 있음.
  • open 이후에 fail 멤버 함수를 통해 fail비트 또는 bad비트가 켜졌는지를 확인함.
    • failbit
      • 입력 작업 시 내부적인 논리 오류로 인해 발생되는 오류
      • ex) 입력받기를 기다리는 값이 오지 않는 문제
    • badbit
      • 스트림의 완전성이 깨진 경우(하나의 스트림에 여러 작업이 진행)

std::ofstream

  • output file stream
  • ifstream과 마찬가지로 객체 생성시에 파일명을 바로 넘겨줄 수도 있음.
  • 연산자 <<
    • 삽입 연산자를 오버로딩 한다.

구현 과정

  1. infile open
  2. outfile 생성 후 open
  3. infile 스트림을 한 줄씩 읽어서 str에 저장
    1. eof를 만날 때까지 반복
    2. 한 줄마다 개행문자 추가
  4. 해당 줄(str)에서 s1을 find
    • 찾은 첫 번째 인덱스를 반환
  5. 해당 인덱스에서 s1을 erase 후 s2를 insert
  6. s2 길이만큼 뒤로 간 뒤에 다시 find
    • pos값이 npos (size_t의 최대값, find가 아무것도 찾지 못했을 때의 반환값)일 때까지 반복

Ex05

주요 개념

멤버 함수 포인터

  • 선언 방법

    1
    
      int	(*f)(void);
    
  • 사용 예시

    1
    2
    3
    4
    5
    6
    7
    
      int	main() {
      	int	(*f)(int);
        
      	f = functionA; // 함수 functionA를 함수 포인터 f에 저장
        
      	std::cout << f(5) << std::endl;
      }
    

Q&A

  • 다음과 같이 호출한 이유

    1
    
      (this->*f[i])();
    
    • 연산자의 우선순위 때문에 함수를 괄호로 감싸야 함.

Ex06

주요 개념

switch문

  • case에 일치한다면 다음의 종료조건을 만나기 전까지 레이블을 계속 실행한다.
    • switch 블록의 끝에 도달한 경우
    • return 문이 발생한 경우
    • goto 문이 발생한 경우
    • break 문이 발생한 경우

요구 사항

  • switch문의 case 조건을 만족하면 해당 조건부터 아래의 모든 조건들을 전부 실행해야함.

Q&A

  • switch문에서 break의 역할
    • switch문은 case를 만족하면 계속 실행하기 때문에 break로 해당 case만 실행되도록 해준다.
  • switch문에 break를 사용하는 경우
    • 아래는 동일한 코드를 중복해서 작성하지 않고 1,2,3일때 모두 하나의 코드로 실행하는 경우이다.
      • 이처럼 switch문을 통해 효율적으로 구성할 수 있다.
    • switch문의 이러한 구현을 fallthrough라고 한다.
      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      
        int x = 2;
        int y = 0;
      
        switch (x) {
            case 1:
            case 2:
            case 3:
                y = 10;
                break;
            case 4:
                y = 20;
                break;
            default:
                y = 30;
                break;
        }
      
  • case에 break를 사용하지 않으면 다음과 같이 implicit-fallthrough 경고가 발생한다.
    1
    2
    3
    
      Harl.cpp:44:24: error: this statement may fall through [-Werror=implicit-fallthrough=]
          44 |             this->debug();
             |             ~~~~~~~~~~~^~
    
    • 이를 방지하기 위해 사용하는 [[fallthrough]] 키워드는 C++17 이후부터 사용이 가능하다.
    • 대신 이전 버전에서는 주석으로 다음과 같이 fall through임을 명시하여 컴파일 경고를 피할 수 있다.
      1
      2
      3
      4
      5
      
        /* Falls through. */
        /* fall-thru */
        /* Else falls through. */
        /* FALLTHRU */
        /* ... falls through ... */
      
    • 예시
      1
      2
      3
      4
      5
      6
      7
      8
      
        switch(i) {
            case 0:
                this->debug();
                // falls through
            case 1:
                this->info();
                // falls through
        ... }
      

Ref.

This post is licensed under CC BY 4.0 by the author.

CPP Module 00 : C++ 기초

CPP Module 02 : OCCF, 연산자 오버로딩