Study/Passionate C++ Programming

[열혈 C++ 프로그래밍] (2) C언어 기반 C++ 2

코딩뚜벅이 2024. 1. 21. 12:31

C언어 기반 C++ 2

  • C언어 기반 C++
  • bool 자료형
  • 참조자의 이해
  • 참조자와 함수
  • malloc & free를 대신하는 new

C언어 기반 C++

const

변수, 객체의 상수화 키워드

 

const int* ptr1 = &val


-> ptr1을 이용하여 val1의 값을 변경 할 수 없음

 

 

 

- const 변수는 반드시 선언과 동시에 초기화
-> 멤버 변수를 const로 선언하는 경우에는 반드시
초기화 리스트(initialize list) 사용
-> Bar의 num은 초기화가 아닌 const int num;
을 선언 한 이후 num = 1;을 시도하는 것

 

 

 

- const 포인터
-> const가 맨 앞에 있으면서 포인터 변수가 가리키
는 값을 상수화를 하는 경우에는 *ptr 상수화
-> const 위치가 자료형과 이름 사이에 있으면 포인
터 변수 자체인 ptr을 상수화
- 멤버함수를 const로 선언하는 경우

 

 

- 멤버함수를 const로 선언하는 경우
-> 해당 멤버 함수 내의 모든 멤버 변수를 상수화
-> 멤버변수 num은 변경 불가
-> 지역변수 a는 변경 가능

 

메모리 공간

- 데이터 영역 : 전역변수 저장 +프로그램 실행부터 끝까지 사용되는 메모리
- 스택 영역 : 지역변수 저장 + 프로그램 실행과정에서 필요한 메모리(함수 호출 등)
- 힙 영역 : 할당과 해제를 통해 생성/소멸 되는 메모리

 

call by value

값에 의한 호출
- 외부에서 내부 메모리 접근 및 변경 불가

 

call by reference

참조에 의한 호출
- 주소값을 통한 접근으로 포인터 특성 상 외부 메모리의 접근 및 변경 가능

 

 

- 참조에 의한 호출
인자를 넘겨주는 경우 매개변수 만큼의 메모리의 재할
당이 일어남
-> 참조를 통해 메모리 재할당 없이 메모리에 접근

 


 

bool 자료형

참/거짓을 나타내는 자료형 -> true&false

 


 

참조자의 이해

기존에 선언된 변수에 할당된 메모리 공간에 새롭게 접근 할 수 있는 방법
- 기존에 선언된 변수에 &를 붙이면 단순 주소값 반환 <-> 새롭게 선언되는 변수에 &를 붙이면 참조 연산자
- 참조 연산자는 기존 선언된 변수에 붙는 별칭 <-> 기존 변수명과 동일한 역할
- 새로운 메모리 공간이 할당되는 것이 아닌 기존에 할당된 메모리 공간에 접근 하는 것
- 참조자를 대상으로 참조자 선언 가능
+ 참조자는 생성과 동시에 참조 (int &ref; -> X)
+ null로 초기화 불가능
+ 참조하는 대상을 변경하는 것은 불가능
+ 배열과 같이 변수의 성향을 지니는 대상은 참조자 선언이 가능

 


상수를 대상으로 선언 불가능 <-> const형으로는 상수를 대상으로 참조 가능

const int &ref=30;


-> 상수를 메모리에 일시적으로 저장하기 때문에 리터럴 상수라도 다음 행에서 소멸되지 않음

 


+ 매개변수형이 const 참조자인 경우 상수를 전달 할 수 있게 하기 위함 <-> const가 아니라면 변수

int Func(const int &num1, const int &num2) { return num1+num2; }

 


참조자를 사용하여 포인터를 사용하지 않고 힙 영역에 접근 가능

int main() {
	int *ptr = new int;
	int &ref = *ptr;
    ref = 20;
    cout << *ptr << endl;
    cout << ptr << endl;
}

 

-> ptr 포인터 변수에 int형 메모리 공간을 할당
-> ptr 포인터가 가리키는 메모리 공을 ref 변수로 참조
-> ptr과 ref에게 할당된 동일 메모리 공간에 20이라는 값을 대입
-> *ptr 출력 시 메모리 공간 내 20이라는 값 출력
-> ptr 출력 시 메모리 공간의 주소값 출력

 


 

참조자와 함수

매개변수는 함수가 호출될 때 인자가 전달되면서 초기화
-> 참조자는 초기화가 필수, 매개변수로 참조자가 사용되면 호출되는 과정에서 초기화
-> 호출된 함수 내에서만 참조자가 사용되고 함수를 빠져나와 메인스택에서는 기존 변수명으로 사용
+ 함수의 정의 형태와 호출 형태를 통해서 원본의 형태를 알 수 없고 함수 몸체의 매개변수를 확인해야 함
+ 함수 내부에서 참조자를 통한 값의 변경이 이루어질 수 있기 때문에, 변경이 이루어지지 않는다면 const

void Func(const int &ref)

 

-> 참조자를 통한 변경이 이루어지지 않음을 판단 할 수 있음

 

 

참조자 반환형

1. 참조자로 참조형 반환값을 받는 경우

 int& Func1(int &ref1) {
    ref1 ++;
    return ref1;
    }
    int main() {
    int val1 = 1;
    int &val2 = Func1(val1);
    val1++;
    val2++;
    return 0;
}

 

-> 1이라는 값이 들어가 있는 val1이라는 메모리 공간 할당
-> val1메모리 공간에 ref1이라는 별칭 생성
-> 참조형 반환값을 참조자로 받아서 val2라는 별칭이 추가 생성
-> 매개변수로 선언된 참조자는 지역변수와 동일한 성격이기에 반환과 동시에 ref1은 소멸
-> val1과 val2는 같은 메모리 공간을 가리키기 때문에 같은 공간에 대해 연산을 진행

 


2. 변수로 참조형 반환값을 받는 경우

int& Func1(int &ref1) {
    ref1 ++;
    return ref1;
    }
    int main() {
    int val1 = 1;
    int val2 = Func1(val1);
    val1++;
    val2++;
    return 0;
}


-> 1이라는 값이 들어가 있는 val1이라는 메모리 공간 할당
-> val1메모리 공간에 ref1이라는 별칭 생성
-> 변수 val2는 새로운 공간을 할당받아 ref1의 값을 복사하여 생성
-> ref1 소멸
-> val1과 val2는 다른 메모리 공간을 가리키기 때문에 각각의 공간에 대해 연산을 진행

 


3. 반환형이 기본자료형으로 선언된 함수
반환 값은 반드시 변수로 받아야 함
-> 기본 자료형으로 반환 시 이는 상수와 동일, 참조자는 변수에 대해서만 참조가 가능하다는 규칙

 

 

- 반환형이 기본 자료형, 매개변수가 참조자
-> num1이라는 메모리 공간을 매개변수 arg가 참조
-> int형으로 반환하여 num2라는 새로운 메모리 공간할당
-> num2와 num1의 메모리 공간이 별도로 존재

 

 

- 반환형이 참조자, 매개변수도 참조자
-> num1이라는 메모리 공간을 매개변수 arg가 참조
-> int 참조형으로 반환하여 num2에 반환
-> num2와 num1은 같은 메모리 공간을 가리킴

 


 

malloc & free를 대신하는 new & delete

new 연산자

메모리 공간의 동적 할당 연산
+ 자료형에 맞는 포인터를 반환 <-> malloc : 자료형이 결정되지 않은 void 포인터 반환

 int* arr = new int[3];

 

-> int형 포인터 arr에 int형 메모리 공간을 할당

 

변수가 실제로 사용되지 않으면 낭비되는 메모리가 발생
-> 고정 배열을 포함한 대부분 일반 변수는 스택 메모리에 저장
-> 일반적으로 스택은 1MB~2MB 설정
-> 이 크기를 초과하면 스택 오버플로 발생
- 동적 할당은 스택 영역이 아닌 힙 영역의 메모리 풀에 할당

 

 

delete 연산자

new로 동적할당 생성된 메모리 공간을 소멸시키는 연산

delete []arr;

 

 

댕글링 포인터
: 할당이 해제된 메모리를 가리키는 포인터
-> 댕글링 포인터를 역참조하면 정의되지 않은 동작

 

 


 

C++에서 C언어 표준 함수 호출

C : #include<stdio.h> / #include<string.h> / #include<math.h>
C++ : #include<cstdio> / #include<cstring> / #include<츰소>
-> c를 붙이고 .h를 제외시키는 규칙성