580 likes | 671 Views
VC++ 10 과 C++0x. 발표자 : 최재혁. 왜 이런것을 알아야 할까 ? C++0x 에 대해서 auto s tatic_assert Rvalue Reference l ambda d ecltype nullptr. 서두. 왜 이런 것을 알아야 할까요 ?. 서두. 너만 모른다 . C++ 의 문제점 > 생산성이 중요해짐. 서두. C++ 이 왜 어려울까요 ? ( 질문 게시글 ). 서두. C++ 이 시대에 뒤 떨어진 프로그래밍 언어일까 ?. C++0x 에 대해서.
E N D
VC++ 10과 C++0x 발표자 : 최재혁
왜 이런것을알아야 할까? • C++0x에 대해서 • auto • static_assert • Rvalue Reference • lambda • decltype • nullptr
서두 • 왜 이런 것을 알아야 할까요?
서두 • 너만 모른다. • C++의 문제점 > 생산성이 중요해짐
서두 • C++이 왜 어려울까요? (질문 게시글)
서두 • C++이 시대에 뒤 떨어진 프로그래밍 언어일까?
C++0x에 대해서 • 정의 : 표준( C++98, C++03 ) • 코어 언어의 기능 추가, 표준 C++ 라이브러리(STL)를 확장 • 그래서 현재..C++98, C++03 보다 성능이 약 40% 정도 증가
C++0x에 대해서 • C++0x는 성능 중심으로도 발전했지만 생산성 중심으로도 발전을 하였다. 나는 그 생산성을 늘리기 위한 방법 중 하나로 이번 스터디를 시작하겠다.
auto • C#의 var • 변수 type을 명시적으로 지정하지 않아도 된다. • 기존의 동적언어는type을 실행시 지정하지만 컴파일 할 때 결정 • 코딩이 간편해지고, 코드 가독성이 좋아짐
static_assert • Assert와 비슷한 조건 조사를 할 수 있음 • 컴파일 타임 때 사용하여 프로그램 실행 전에 문제를 찾을 수 있음 • 템플릿 프로그래밍에 사용하면 특히 유용
static_assert • PLAYER* pPlayer;……….assert( NULL != pPlayer ); • assert는 실행 시에 사용하고, #error는 프리프로세스에 사용하기 때문에 템플릿 실체화시에는 이것들을 사용 할 수 없다. • static_assert는 컴파일 타임에서 조사한다.
static_assert • static_assert(“constant-expresstion” , “error-message”);
static_assert • 예제 • static_assert ( sizeof(int) == 4, “not size”)
RValue Reference • C++0x에서는 이런 불필요한 복사를 방지하는 기능을 제공 -> 성능적인 측면에서 개선 • 메모리 할당, 복사, 해제 비용을 줄이는데 성공
RValue Reference • L Value와 R Value int a = 10; int b = 100; b = a;
RValue Reference • *ptr, ptr[index], ++x => L Value • 1729, x+y, std::string(“C++”), x++ => R Value
RValue Reference • 식이 끝난 후 계속 존재하는 값=> L Value • 식이 끝나면 존재하는 않는 값, 임시값=> R Value
RValue Reference void main() { intnCount = 0; nCount; 0; PLAYER Player; Player; PLAYER(); Render(); }
RValue Reference • L Value Reference란? int a = 10; int& refA = a;
RValue Reference • R Value Reference란int&& refA = 119;
RValue Reference • 에러가 생기는 곳은?intnCount;int& refValue1 = nCount;int& refValue2 = 10;int&& rrefValue1 = 10;int&& rrefValue2 = nCount;
RValue Reference • Move semantics • 불필요한 연산을 없앨 수 있다고 했는데 불필요한 복사를 없앨수 있는 것은 바로 R Value Reference의 Move semantics 덕분이다. • ‘move 생성자’ ‘move 대입 연산자’ 개념이 등장 (연산자 && 사용) • 클래스를 정의할 때 move 생성자난move대입연산자를 정의하면 어떤 오브젝트에서 다른 오브젝트로 리소스를 복사가 아닌 이동이 가능
RValue Reference • 주의점 NPC npc7; NPC npc8; Npc9 = std::move(npc7); .. .. <<< 이후 npc7을 사용 할수 있을지 없을지 X
RValue Reference • 식이 끝난 후 계속 존재하는 값은 좌측 값, 식이 끝나면 존재하지 않는 값은 임시 값은 우측 값 • 좌측 값 참조는 좌측 값을 참조하고, 우측값 참조는 우측값을 참조한다. • 불필요한 복사를 없앨 수 있는 것은 바로 우측 값 참조의 move semantics 덕택. • move 생성자, move 연산자는 암묵적으로 만들어 지지 않으면 복사생성자가 move 생성자 보다 우선 순위가 높고, 대입 연산자가 move 대입 연산자 보다 우선 순위가 높다. • 표준 라이브러리에서 제공하는 std::move를 사용하면 좌측 값을 우측 값으로 타입 캐스팅 할 수 있다. • 우측 값 참조와 좌측 값 참조는 타입이 다르므로 함수 오버로드를 적용할 수 있다. • 우측 값 참조는 우측 값이 아니다. • std::forward 함수는 좌측 값은 좌측 값으로, 우측 값은 우측 값으로 캐스팅 해준다.
nullptr • Nullptr이 필요한 이유 • C++03 까지는 NULL 매크로 사용 • 문제점 : NULL매크로나 0을 사용하여 함수에 인자로 넘기는 경우 int타입으로 추론되는 문제가 존재
nullptr void func(int a){ cout << “fun >>> int” << endl; } void func(double *p) { cout << “func >>> double” << endl; } void main() {func(static_cast<double*>(0)); func(0); func(NULL);getchar();}
nullptr • 사용방법 -> 0이나 NULL을 nullptr로 대체 • char* p = nullptr; • func(nullptr); 로 호출 • nullptr은 클래스다. • sizeof(nullptr) => 4
decltype • auto와 같이 타입을 결정 • 함수의 반환값으로 타입 결정가능 • 변수들의 계산 결과로 타입 결정 가능
decltype int HP;decltype(HP) NPCHp = 5; decltype(HP + NPCHp) TotalHp; decltype(HP*) pHP = &HP;
lambda • STL 알고리즘! 이제 쉽게 쓰자 • 펑터(functer)! 그 귀차니즘에서 벗어나다. • 펑터? <코드> boolIsBig(int a, int b) { return a > b; } void main { vector<int> array; //...... sort(array.start(), array.end(), IsBig(inta, int b)); } </코드>
lambda • 람다란? • 익명의 함수 • 간단한 함수 • 실제로 함수포인터와 거희 동일하다. • 람다의 형식 <코드> [] // 람다의 캡처 () // 함수의 인수(파라미터) () // 함수의 본체 () // 함수의 본체 </코드>
lambda • 예제 <코드> void main() { [] { cout << “Hello, TechDay!” << endl; } (); } </코드>
lambda • 예제 (auto를 사용하면 변수에 대입가능) <코드> void main() { auto func1 = [] { cout << “Hello, TechDay!” << endl; } (); }; func(); } </코드>
lambda • 예제(함수의 인자로 사용) <코드> Template< typenameFunc > void Test( Funcfunc ) { func(); } void main() { auto func1 = [] { cout << “Hello, TechDay!” << endl; } (); }; Test(func1); } </코드>
lambda • 예제 (파라미터 사용) <코드> void main() { auto func1 = [](int n ) { cout << “Hello, TechDay!”<< n << endl; } (); }; func1 (123); func1 (345); } </코드>
lambda • 예제 (파라미터 사용) <코드> void main() { auto func1 = [] { return 3.14; }; auto func2 = [] (float f) { return f; }; auto func3 = [] () -> float { return 3.14; }; float a1 = func1 (); float a2 = func2 ( 3.14f ); // warring float a3 = func3 (); } </코드>