반응형

 

함수 오버로딩(Function overloading)

- C에서는 동일한 이름의 함수가 정의되는것을 허용하지 않는다.

- C++에서는 함수에 전달되는 인자를 통해서 호출하려는 함수의 구분이 가능하다.

- 그렇기 때문에 매개변수의 선언형태가 다르다면 동일한 이름의 함수를 정의할 수 있다.

  ※ C에서는 함수의 이름만 이용해서 호출되는 대상을 찾는 반면, C++에서는 함수의 이름과 매개변수 선언 두 가지 정보를 이용해 호출 대상을 찾는다.

#include <iostream>
using namespace std;

void Func(int n)
{
    cout << n << endl;
}

void Func(char c)
{
    cout << c << endl;
}

void main()
{
    Func(10);
    Func('A');
    
    //결과
    //10
    //A
}

 

 

 

 

Default 매개변수

- 단어 그대로 기본적으로 설정되어 있는 매개변수라고 생각하면 된다.

- 함수를 호출했을 때, 매개변수 값을 전달하지 않으면 자동으로 기본값을 가진다.

- Default 값은 함수의 원형에만 위치시켜야한다.

#include <iostream>
using namespace std;

class Test
{
public:
    void Func(int n1 = 10, int n2 = 20);
};

void Test::Func(int n1, int n2)
{
    cout << n1 + n2 << endl;
}

void main()
{
    Test test;
    test.Func();
    
    //결과 30
}

 

 

부분적 Defualt 값 설정

- 반드시 모든 매개변수가 Default 값을 가질 필요는 없다.

- 다음과 같은 경우에 부분적 Default 값을 저장할 수 있다.

  • 반드시 오른쪽 매개변수의 Default 값부터 채우는 형태로 정의한다.
void Func(int n1, int n2 = 20, int n3 = 10)
  • Default 매개변수로 인해 형성되는 모호한 오버로딩은 허용하지 않는다.
#include <iostream>
using namespace std;

class Test
{
public:
    void Func();
    void Func(int n1 = 10, int n2 = 20);
};

void Test::Func()
{
    cout << 100 << endl;
}

void Test::Func(int n1, int n2)
{
    cout << n1 + n2 << endl;
}

void main()
{
    Test test;
    test.Func(); //에러
}
반응형

'Stack > C++' 카테고리의 다른 글

C++ 업캐스팅, 오버라이딩, 가상함수  (0) 2021.11.08
C++ 클래스 상속  (0) 2021.11.04
C++ this 포인터  (0) 2021.10.24
C++ 복사 생성자 심화  (0) 2021.10.17
C++ 파일 입출력 ofstream, ifstream  (0) 2021.10.16
반응형

 

this 포인터

- 자신을 가리키는 포인터이다.

- 객체의 0번째 멤버변수라고도 한다.

- 멤버함수에서 멤버변수에 접근하기 위해 사용한다.

class Test
{
private:
    int num1, num2;
public:
    void Add(int num1, int nm2)
    {
        //num1과 num2는 전부 지역변수이다.
        num1 = num1;
        num2 = num2;
        
        //그렇기 때문에 this 포인터로 멤버변수를 명시해준다.
        this->num1 = num1;
        this->num2 = num2;
    }
};
  • 변수명이 동일하면 제일 가까운 위치에 있는 변수로 취급된다.
  • 그렇기 때문에 this 포인터로 멤버변수를 구분해준다.
반응형

'Stack > C++' 카테고리의 다른 글

C++ 클래스 상속  (0) 2021.11.04
C++ 함수 오버로딩, Deault 매개변수  (0) 2021.10.24
C++ 복사 생성자 심화  (0) 2021.10.17
C++ 파일 입출력 ofstream, ifstream  (0) 2021.10.16
C++ 생성자, 복사생성자, 소멸자 (+ const)  (0) 2021.10.15
반응형

 

※ 들어가기에 앞서 참조자와 복사 생성자에 대한 사전 지식이 필요하니 다음 글을 참조

 

C++ 생성자, 소멸자 (+ const)

들어가기에 앞서... const - const 변수 : 해당 변수를 정보 변경이 불가능한 상수로 변환. - const 함수 : 해당 함수에서 const의 위치에 따라 정보의 변환을 막거나 반환값을 상수로 바꾼다. 1. const 변수

srdeveloper.tistory.com

 

C++ 참조자(Reference)

참조자 (Reference) - 할당된 어떤 하나의 메모리 공간에 다른 이름을 부여하는 것이다. ※ 별명이라고 생각해도 좋다. - 참조자는 변수 앞에 &를 붙여줌으로써 선언할 수 있다. ※ 이미 선언된 변수

srdeveloper.tistory.com


깊은 복사, 얕은 복사

- 깊은 복사 : 값이 복사되는 복사

- 얕은 복사 : 참조 값이 복사되는 복사

 

 

 

디폴트 복사 생성자의 문제점

- 앞서 생성자, 소멸자 포스팅에서 복사 생성자는 정의하지 않아도, 디폴트 복사 생성자가 자동으로 삽입된다.

- 하지만, 반드시 복사 생성자를 정의해야 하는 경우가 있다.

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>
#include <string>
using namespace std;

class Test
{
private:
	
    char* cArr;
public:
    Test(const char* cArr)
    {
        int len = strlen(cArr) + 1;
        this->cArr = new char[len];
        strcpy(this->cArr, cArr);
    }
    void Show()
    {
        cout << "cArr : " << cArr << endl;
    }
    ~Test()
    {
        delete cArr;
        cout << "Called destructor" << endl;
    }
};

void main()
{
    Test t1("Test string");
    Test t2 = t1;
    t1.Show();
    t2.Show();
    
    //결과
    //cArr : Test string
    //cArr : Test string
    //Called destructor
}
  • 위와 같이 char 포인터를 디폴트 복사 생성자로 복사가 일어나게 되면 얕은 복사가 일어난다.
  • 즉, 참조값이 복사가 되기 때문에 t2객체와 t1객체의 cArr 포인터가 참조하는 문자열은 같다고 볼 수 있다.
  • 그렇기 때문에 어떤 객체의 소멸자에서 cArr이 참조하는 문자열을 delete로 할당해제 하면 남은 객체에서는 이미 지워진 문자열을 대상으로 delete 연산을 하기 때문에 문제가 된다.
  • 따라서 복사 생성자를 정의할때에는 이러한 문제가 발생하지 않도록 신경써야한다.

 

 

 

복사 생성자의 호출 시점

- 복사 생성자의 호출 시점은 3가지로 구분된다.

  • 기존에 생성된 객체를 이용해서 새로운 객체를 초기화할 때
SomeClass sc1;
SomeClass sc2 = sc1;
  • Call by value 함수호출 과정에서 객체를 인자로 전달할 때
SomeClass Func(SomeClass sc)
{
    ...
}

void main()
{
    SomeClass sc;
    Func(sc)	// 호출하게 되면 매개변수 sc가 할당되는 동시에 초기화
}
  • 함수에서 객체를 참조형으로 반환하지 않을 때
SomeClass Func(SomeClass sc)
{
    return sc	// 반환할 때 메모리 공간이 할당되면서 동시에 초기화
}

void main()
{
    SomeClass sc1;
    SomeClass sc2 = Func(sc1);
}

  ※ 즉, 위 코드에서 반환되는 sc의 객체는 인수로 받은 sc가 아니라 '임시객체'가 만들어져 이 '임시객체'에서 복사 생성자가 호출되어 return에 명시된 객체가 인자로 전달된다.

 

 

 

임시객체, 소멸시점

- 클래스 외부에서 객체의 멤버함수에 접근하는 방법은 다음 세가지이다.

  • 객체에 붙여진 이름
  • 객체의 참조 값 (임시객체)
  • 객체의 주소 값

- 임시객체가 생성된 위치에는 임시객체의 참조 값이 반환된다.

- 그렇기 때문에 다음과 같은 구성이 가능하다.

#include <iostream>
using namespace std;

class Test
{
private:
    int n;
public:
    Test(int n)
    {
        cout << "Create" << endl;
        this->n = n;
    }
    void Show()
    {
        cout << n << endl;
    }
    ~Test()
    {
    	cout << "Destroy" << endl;
    }
};

void main()
{
    Test(100).Show();
    cout << "-----" << endl;
    const Test& t = Test(200);
    cout << "-----" << endl;
    
    //결과
    //Create
    //100
    //Destroy
    //-----
    //Create
    //-----
    //Destroy
}
  • 참조자는 '임시객체'에 대한 참조가 가능하기 때문에 위와 같이 사용이 가능하다.
  • 이 임시객체는 반환된 뒤 다음 줄로 넘어가면 자동으로 소멸 되지만, '임시객체'에 대한 참조자가 존재하면 바로 소멸되지 않는다.

※ 복사 생성자가 일어나지 않는 예외

SomeClass Func()
{
    return SomeClass
}

void main()
{
    SomeClass sc = Func();
}
  • 위의 코드에서 sc 객체를 생성해서, Func()에서 반환되는 객체를 가지고 대입연산을 진행하는것으로 이해할수도 있지만 위와 같은 상황에서는 객체를 생성하지 않고 반환되는 임시객체에 sc라는 이름을 할당한다고 보면 된다. (객체의 생성 수를 하나 줄여서 효율성을 높이기 위해서이다.)
반응형

'Stack > C++' 카테고리의 다른 글

C++ 함수 오버로딩, Deault 매개변수  (0) 2021.10.24
C++ this 포인터  (0) 2021.10.24
C++ 파일 입출력 ofstream, ifstream  (0) 2021.10.16
C++ 생성자, 복사생성자, 소멸자 (+ const)  (0) 2021.10.15
C++ 동적할당 new, delete  (0) 2021.10.13
반응형

 

문자열 뒤집기

- 문자열의 n번째 순서와 마지막에서 n번째 순서의 위치를 변경해준다. (n의 값은 동일)

- 단순하게 생각하면 문자열의 길이만큼의 loop를 돌면서 위치를 변경해줘도 되지만, 위와 같은 swap 방식을 사용하면 문자열 길이의 반만 돌아도 뒤집기가 가능하기 때문에 훨씬 효율적이다.

#include <iostream>
using namespace std;

void Swap(char* c1, char* c2)
{
    char tmp = *c2;
    *c2 = *c1;
    *c1 = tmp;
}

void main()
{
    string str = "string";
    for(int i = 0; i < str.length() / 2; i++)
    {
    	Swap(&str[i], &str[str.length() - i - 1]);
    }
    cout << str << endl;
    
    //결과 : gnirts
}

 

 

 

 

숫자 뒤집기

- 숫자를 뒤집는 방법은 단순하게 2가지로 분류해볼 수 있다.

  • 숫자를 문자열로 변경해 문자열을 뒤집은 후 문자열을 숫자로 변환.
  • 수식을 사용해 뒤집기.

- 수식을 사용해서 숫자를 뒤집는 방법은 다음과 같다.

  1. 뒤집을 숫자를 10으로 나눠 나머지를 구한다.

  2. 나머지를 임시 변수에 더한다.

  3. 뒤집을 숫자를 10으로 나눠준다.

  4. 10으로 나눠진 뒤집을 숫자가 0이면 반복문을 빠져나간다.

  5. 10으로 나눠진뒤집을 숫자가 0이 아니면 임시 변수에 10을 곱해준다.

- 위의 과정에서 반복문을 빠져나오면 임시변수의 값이 뒤집을 숫자가 뒤집어진 값이 완성된다.

#include <iostream>
using namespace std;

void main()
{
    int n = 100;
    int reverse = 0;
    while(true)
    {
    	reverse += n % 10;
        n /= 10;
        if(n == 0)
        {
            break;
        }
        reverse *= 10;
    }
    cout << reverse << endl;
    
    //결과 : 1
}
반응형

'Stack > Algorithm' 카테고리의 다른 글

[유니티 C#] 퀵 정렬(Quick sort) 구현  (0) 2022.10.06
퀵정렬(Quick Sort) 구현  (0) 2021.09.19
삽입정렬(Insertion Sort) 구현  (0) 2021.09.18
선택정렬(Selection Sort) 구현  (0) 2021.09.15
버블정렬(Bubble Sort) 구현  (0) 2021.09.14
반응형

 

※ C의 파일 입출력은 다음 링크에서 확인

 

C 파일 입출력

파일 입출력 - 프로그램 내의 정보를 외부 파일에 저장하거나 외부 파일의 정보를 프로그램으로 불러오는 방식. ※ 스트림 : 구현한 프로그램과 참조할 데이터가 저장되어 있는 파일 사이에 놓

srdeveloper.tistory.com


 

파일 입출력

- 프로그램 내의 정보를 외부 파일에 저장하거나 외부 파일의 정보를 프로그램으로 불러오는 방식

- 필요 헤더 : <fstream>

- 파일 내용 출력 : << 내용

- 파일 내용 입력 : >> 내용

 

 

 

ofstream

- 쓰기모드 형태로 파일 정보를 담는다.

- 파일이 없을경우 파일을 생성한다.

- ofstream.save(FileName, OpenMode)

  • OpenMode : default값은 덮어쓰기 모드이며, 파일 내용을 덧붙이려면 ios::app를 입력한다.

- ofstream.close()

  • 스트림을 해제하는 함수.
#include <fstream>
using namespace std;

void main()
{
    ofstream f;
    f.open("Temp.txt");
    if(f.is_open())
    {
        f << "Empty" << endl;
        f.close();
    }
}

 

 

 

 

ifstream

- 읽기모드 형태로 파일정보를 담는다.

- 파일이 없을경우 NULL을 반환한다.

- >>

  • 띄어쓰기 또는 개행단위로 문자열을 가져온다.

- getline(ifstream, string)

  • 개행단위로 문자열을 가져온다.
  • 필요 헤더 : <string>
#include <fstream>
#include <string>
using namespace std;

void main()
{
    ifstream f;
    string str;
    f.open("Temp.txt");
    
    //1. >> 연산자
    while(!f.eof())
    {
        f >> str;
    }
    
    //2. getline()
    while(!f.eof())
    {
        getline(f, str);
    }
}
반응형

'Stack > C++' 카테고리의 다른 글

C++ this 포인터  (0) 2021.10.24
C++ 복사 생성자 심화  (0) 2021.10.17
C++ 생성자, 복사생성자, 소멸자 (+ const)  (0) 2021.10.15
C++ 동적할당 new, delete  (0) 2021.10.13
C++ 참조자(Reference)  (0) 2021.09.29

+ Recent posts