Effective C++/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;
};
- 눈여겨볼 점들
- 클래스와 구조체?
- 취향껏 골라서 사용한다.
- 템플릿 매개변수에는 const, & 등은 기입하지 않는다.
- 포인터는 기입할 것
- 어댑터에서 operator()는 하나의 함수객체 안에는 하나만 존재해야 한다.
- 클래스와 구조체?
728x90