안녕하세요. 파피몬입니다.
이 복습 내용은 최호성 선생님의 "이것이 C++이다"를 공부하고 작성하였습니다.
아직 모르는 게 많은 학생이라 오개념이 있을 수 있습니다. 친절하게 댓글로 알려주시면 좋은 공부 될 것 같습니다!!
2단원에서는 1단원에 이어서 C언어와 C++의 차이점에 주안을 두고 공부하였습니다.
Chapter 2. C++ 함수와 네임스페이스
1. C++에서는 C언어와 달리 다형성(함수를 여러형태로 구현하고, 동시에 존재하는 것)을 지원한다. 고로 이름이 같지만 매개변수가 다른 함수를 정의할 수 있다. 이를 다중 정의(overloading)이라고 한다.
2. C++에서는 디폴트 매개변수를 지원한다. 함수 원형의 선언부에 디폴트 값을 기술한다. 반드시 오른쪽 매개변수부터 기술해야 하며, 중간에 빼먹는 매개변수가 있으면 안된다!
3. 위의 다중 정의와 디폴트 매개변수가 조합된다면 '모호성'이 발생할 수 있다! 그럼으로 다중 정의는 함수 템플릿으로 대체하고, 디폴트 매개변수는 사용을 지양하는 편이 현명하다!
#include<iostream>
using namespace std;
void TestFunc(int a)
{
cout<< "TestFunc(int)" <<endl;
}
void TestFunc(int a, int b=10)
{
cout<< "TestFunc(int, int)" <<endl;
}
int main()
{
//오버로드된 함수에 대한 호출이 모호합니다!
TestFunc(5)
return 0;
}
4. 함수 템플릿으로 사용자의 편의성과 확장성을 얻을 수 있다! caller함수가 변수의 형식을 결정한다. 디버거에서는 마치 해당변수가 이미 들어가 있는 형식으로 작동한다.
#include<iostream>
using namespace std;
template<typename T>
T TestFunc(T a)
{
cout<<"매개변수 a: "<<a<<endl;
return a;
}
int main()
{
//디버거에서는 int TestFunc(int a)로!
//TestFunc<int>(3)으로 형 지정도 가능하다!
cout<<"int\t"<<TestFunc(3)<<endl;
//디버거에서는 double TestFunc(double a)로!
//TestFunc<double>(5.3)으로 형 지정도 가능하다!
cout<<"double\t"<<TestFunc(5.3)<<endl;
return 0;
}
5. C++에서 재정의, 다중정의 등으로 함수의 이름을 중복해서 쓸 수 있게 하는 것 같지만, 실질적으로 컴파일을 돌려보면 Name Mangling이 적용되어 함수의 본명(?)은 겹치지 않게 선언이 알아서 된다.
//컴파일러를 돌려보면 (괄호)안에 있는 부분이 함수의 본명이다
"int __cdecl Add(int, int)" (?Add@@YAHHH@Z)
//이를 피하려면 extern "C"를 도입하여 C언어의 방식으로 함수를 컴파일 할 수 있다
//이 말은 곧 이름이 같은 함수는 컴파일 에러를 일으킨다는 뜻이다
extern "C"
{
//둘다 이름이 Add임으로 컴파일 에러!
int Add(int a, int b);
double Add(double a, double b);
}
6. namespace는 C++의 변수/함수/클래스 등을 하나의 소속으로 묶어준다. 이름의 중복 가능성으로 인한 혼동을 방지하며, 이는 규모가 큰 프로그램에서 용이하게 써먹을 수 있다.
7. using이라는 예약어를 통해 **소속::** 을 나타내주는 것 생략할 수 있다.
#include<iostream>
//std::cout -> cout 표현가능!
using namespace std;
namespace TEST
{
int g_nData = 100;
void TestFunc(void)
{
cout<<"TEST::TestFunc()"<<endl;
}
}
using namespace TEST;
int main()
{
//TEST::라고 범위 지정 할 필요X
TestFunc();
cout<<g_nData<<endl;
return 0;
}
--------------------
TEST::TestFunc()
100
8. namespace는 중첩이 가능하여, 큰 소속과 그 안의 소속에 각각 같은 이름으로 변수를 선언 할 수 있다. 정확한 변수에 접근하기 위해서는 정확한 소속을 써주는 것이 중요하다!
9. 전역함수/전역변수와 namespace에서의 함수/변수 이름이 동일하다면, 각각의 namespace를 함수/변수 호출 전 기술함으로써 각각을 구별해 호출한다.
** 위 같은 상황에서 해당 namespace에 using예약어를 선언한다면 '모호성'으로 인한 컴파일 에러 발생!
** 전역함수/전역변수를 호출 시 정확한 방법은 앞에 ::을 추가하여 ::전역함수 / ::전역변수 형식으로 기술하는 것!
10. 혼동되는 식별자 검색 순서
** 전역변수의 경우 선언 순서를 생각해야 한다. 만약 같은 scope에서 변수 호출 전에 변수가 선언이 되어있다면, 그 변수를 호출하고, 그렇지 않다면 그 다음 scope를 탐방해야 할 것! C언어의 전역변수와 비슷하다.
#include<iostream>
using namespace std;
int nData = 200;
namespace TEST
{
int nData = 100;
void TestFunc(void)
{
cout<<::nData<<endl;
cout<<nData<<endl;
}
}
int main()
{
TEST::TestFunc();
return 0;
}
--------------------
200
100
#include<iostream>
using namespace std;
int nData = 200;
namespace TEST
{
void TestFunc(void)
{
cout<<::nData<<endl;
cout<<nData<<endl;
}
int nData = 100;
}
int main()
{
TEST::TestFunc();
return 0;
}
--------------------
200
200
'프로그래밍 언어 > C++' 카테고리의 다른 글
C++ 4단원 복습! (2편) (0) | 2020.03.15 |
---|---|
C++ 4단원 복습! (1편) (0) | 2020.03.14 |
C++ 3단원 복습! (2편) (0) | 2020.03.12 |
C++ 3단원 복습! (1편) (0) | 2020.03.12 |
C++ 1단원 복습! (0) | 2020.03.10 |
댓글