스토리텔링 개발자

[Effective STL] 40. adaptable한 함수 객체(C++98) 본문

개발/Effective STL

[Effective STL] 40. adaptable한 함수 객체(C++98)

김디트 2025. 1. 8. 11:24
728x90

항목 40. 함수 객체 클래스는 어댑터 적용이 가능하게(adaptable) 만들자

 

 

 

  • C++11 이후로는 더 이상 맞지 않는 이야기이므로 참고할 것.
ptr_fun와 adaptable
  • 아래는 잘 동작하는 코드이다.
list<Widget*> widgetPtrs;
bool isInteresting(const Widget* pw);

list<Widget*>::iterator i = find_if(widgetPtrs.begin(),
                                    widgetPtrs.end(),
                                    isInteresting);
if(i != widgetPtrs.end())
{
   ... // interesting한 widget에 대한 첫째 포인터 처리
}
  • 그렇다면 interesting하지 않은 widget을 탐색하려고 하면 아래의 코드는 동작할까?
// 컴파일 에러!
list<Widget*>::iterator i = find_if(widgetPtrs.begin(),
                                    widgetPtrs.end(),
                                    not1(isInteresting));
// ptr_fun을 사용하여 아래처럼 해야 한다.
list<Widget*>::iterator i = find_if(widgetPtrs.begin(),
                                    widgetPtrs.end(),
                                    not1(ptr_fun(isInteresting)));
  • ptr_fun은 함수를 함수 객체로 만들어주는 일을 한다.
    • 근데 사실, 여기서 ptr_fun이 하는 일은 몇 가지 typedef 타입을 제공해주는 것 뿐이다.
  • STL의 4대 표준 함수 어댑터(not1, not2, bind1st, bind2nd) 모두가 이러한 typedef 타입이 있어야 동작한다.
  • adaptable하다는 것은 바로 이런 typedef를 제공하는 것을 뜻한다.
    • C++11에서는 이 typedef들을 더 이상 필요로 하지 않는다.
    • 그렇기 때문에 함수 객체가 std::unary_function 등을 상속받아 구현될 필요도 없다.

 

 

 

adaptable 하기 위한 typedef
  • argument_type
  • first_argument_type
  • second_argument_type
  • result_type
  • 이들은 모두 함수 객체 어댑터 기본 클래스에 포함되어 있다.(std::unary_function, std::binary_function)
    • C++11에서는 더 이상 사용되지 않는다.

 

 

 

함수 객체 어댑터(C++11에서는 사라짐)
// unary_function 상속받은 함수 객체
template<typename T>
class MeetsThreshold : public std::unary_function<Widget, bool>
{
private:
    const T threshold;
public:
    MeetsThreshold(const T& threshold);
    bool operator()(const Widget&) const;
    ...
};

// binary_function 상속받은 함수 객체
struct WidgetNameCompare : std::binary_function<Widget, Widget, bool>
{
    bool operator()(const Widget& lhs, const Widget& rhs) const;
};
  • 눈여겨볼 점들
    1. 클래스와 구조체?
      • 취향껏 골라서 사용한다.
    2. 템플릿 매개변수에는 const, & 등은 기입하지 않는다.
      • 포인터는 기입할 것
    3. 어댑터에서 operator()는 하나의 함수객체 안에는 하나만 존재해야 한다.
728x90
Comments