728x90
반응형
728x90
반응형
728x90
반응형

C++14 : C++11을 더욱 발전시킨 Modern C++

  • C++14C++11을 기반으로 한 소규모 개정판 으로, 기존 기능을 더욱 개선하고 실용적인 기능을 추가한 표준입니다.

  • C++11이 도입한 스마트 포인터, auto, 람다 표현식 등의 혁신적인 기능을 다듬고,
    템플릿과 constexpr의 활용도를 높이는 기능을 포함하여 코드의 가독성과 유지보수성을 향상 시켰습니다.


  • 이번 글에서는 C++14에서 새롭게 추가된 기능들만 정리하여 소개하겠습니다.


1. 반환형 자동 유추 (Return Type Deduction)

  • C++14에서는 함수의 반환형을 auto로 선언하면 자동으로 유추됩니다.

  • cpp

      auto add(int a, int b) { return a + b; } // 반환형이 int로 자동 결정
    

  • 함수의 반환형을 일일이 명시하지 않아도 되므로, 가독성과 유지보수가 쉬워집니다.


2. 제네릭 람다 (Generic Lambda)

  • 이제 람다 함수의 매개변수 타입을 auto로 선언할 수 있습니다.

  • cpp

      auto lambda = [](auto a, auto b) { return a + b; };
      std::cout << lambda(3, 4.5) << std::endl; // 7.5
    

  • 템플릿을 사용하지 않고도 다양한 타입을 지원하는 람다를 쉽게 만들 수 있습니다.


3. decltype(auto)

  • C++14에서는 decltype(auto)를 사용해 반환 타입을 더욱 정밀하게 지정할 수 있습니다.

  • cpp

      int x = 10;
      int& foo() { return x; }
    
      decltype(auto) y = foo(); // y는 int& 타입
    

  • 함수나 변수의 원래 타입을 유지하는 데 유용합니다.


4. constexpr 함수 확장

  • C++14에서는 constexpr 함수 내에서 if문, 반복문 등의 논리를 사용할 수 있습니다.

  • cpp

      constexpr int factorial(int n) {
          int result = 1;
          for (int i = 2; i <= n; ++i)
              result *= i;
          return result;
      }
    

  • 컴파일 타임 연산을 더욱 유연하게 사용할 수 있습니다.


5. unique_ptr 인스턴스 생성 (std::make_unique)

  • C++14에서는 std::unique_ptr을 보다 쉽게 생성할 수 있도록 std::make_unique가 추가되었습니다.

  • cpp

      #include <memory>
      auto ptr = std::make_unique<int>(42);
    

  • 메모리 할당을 안전하고 간결하게 처리할 수 있습니다.


6. 숫자 리터럴 구분자 (Digit Separator)

  • 숫자 리터럴에서 단일 따옴표(')를 사용하여 가독성을 높일 수 있습니다.

  • cpp

      int num = 1'000'000; // 1000000과 동일
    

  • 큰 숫자의 가독성을 개선하는 간단하지만 유용한 기능입니다.


7. 변수 템플릿 (Variable Templates)

  • 템플릿을 변수 로도 선언할 수 있습니다.

  • cpp

      template<typename T>
      constexpr T pi = T(3.141592653589793);
    
      std::cout << pi<double> << std::endl; // 3.14159...
    

  • 템플릿을 변수로 활용할 수 있어 코드가 더욱 간결해집니다.


8. 정수 시퀀스 (std::integer_sequence)

  • 템플릿 프로그래밍에서 정수 시퀀스를 다룰 수 있도록 std::integer_sequence가 추가되었습니다.

  • cpp

      #include <utility>
      template <typename T, T... Ints>
      void print_sequence(std::integer_sequence<T, Ints...>) {
          ((std::cout << Ints << " "), ...);
      }
      
      int main() {
          print_sequence(std::integer_sequence<int, 1, 2, 3, 4>{}); // 1 2 3 4
      }
    

  • 템플릿 메타프로그래밍에서 정수 시퀀스를 더 쉽게 활용할 수 있습니다.


9. 변수 변경 반환 (std::exchange)

  • 값을 다른 값으로 바꾸고, 원래 값을 반환하는 함수가 추가되었습니다.

  • cpp

      #include <utility>
      int x = 10;
      int old_x = std::exchange(x, 20); // x는 20이 되고, old_x는 10
    

  • 객체의 값 변경과 이전 값을 동시에 처리할 때 유용합니다.


정리

  • C++14C++11을 기반으로 더 직관적이고 강력한 코드 작성이 가능하도록 개선된 표준 입니다.

  • 특히 제네릭 람다, constexpr 확장, std::make_unique 은 코드의 간결성과 안전성을 향상시키는 기능들입니다.

  • C++14의 추가 기능을 적극 활용 하여 더 효율적인 코드를 작성해 보세요! 🚀

728x90
반응형
728x90
반응형
// main.cpp (C++11 unique_ptr, shared_ptr, weak_ptr)
// main code from http://www.gisdeveloper.co.kr/?p=2094
#include <memory>
#include <iostream>
using namespace std;
void test_unique_ptr();
void test_unique_ptr2();
void test_shared_ptr();
void test_move();
void test_weak_ptr();
void test_shared_weak_ptr();
int main(int argc, char *argv[])
{
test_unique_ptr();
test_unique_ptr2();
test_shared_ptr();
test_move();
test_weak_ptr();
test_shared_weak_ptr();
return 0;
}
void test_unique_ptr()
{
cout << __FUNCTION__ << endl;
unique_ptr<int> p1(new int(10)); // making unique pointer
cout << *p1 << endl; // 10
}
void test_unique_ptr2()
{
cout << __FUNCTION__ << endl;
unique_ptr<int> p1(new int(10));
cout << *p1 << endl; // 10
// sharing unique pointer.
// unique_ptr<int> p2 = p1; // error: use of deleted function 'std::unique_ptr<_Tp, _Dp>::unique_ptr(const std::unique_ptr<_Tp, _Dp>&) [with _Tp = int; _Dp = std::default_delete<int>]'
}
void test_shared_ptr()
{
cout << __FUNCTION__ << endl;
shared_ptr<int> p1(new int(10)); // making shared pointer
shared_ptr<int> p2 = p1; // sharing shared pointer
cout << *p1 << endl; // 10
cout << *p2 << endl; // 10
cout << p2.use_count() << endl; // 2 (it's a reference count)
p1.reset();
cout << p2.use_count() << endl; // 1
p2.reset();
cout << p2.use_count() << endl; // 0
}
void test_move()
{
cout << __FUNCTION__ << endl;
unique_ptr<int> p1(new int(10)); // making unique pointer
cout << *p1 << endl; // 10
unique_ptr<int> p3 = move(p1); // moving unique pointer (it is not sharing)
// cout << *p1 << endl;
cout << p1.get() << endl; // 0
cout << p3.get() << endl; // pointer
}
void test_weak_ptr()
{
cout << __FUNCTION__ << endl;
shared_ptr<int> sp1(new int(10)); // making shared pointer
weak_ptr<int> wp1 = sp1; // sharing weak pointer
cout << sp1.use_count() << endl; // 1
cout << wp1.use_count() << endl; // 1
}
void test_shared_weak_ptr()
{
cout << __FUNCTION__ << endl;
shared_ptr<int> sp1(new int(10));
weak_ptr<int> wp1 = sp1;
cout << sp1.use_count() << endl; // 1
cout << wp1.use_count() << endl; // 1
{
shared_ptr<int> sp2 = wp1.lock();
cout << sp1.use_count() << endl; // 2
cout << wp1.use_count() << endl; // 2
}
cout << sp1.use_count() << endl; // 1
cout << wp1.use_count() << endl; // 1
}
728x90
반응형

+ Recent posts