generalized functors - realizing command design pattern in c++
DESCRIPTION
This is from my series of lectures on C++ and Design Patterns at Interra. This was first presented in 2008TRANSCRIPT
![Page 1: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/1.jpg)
March 06, 2008
Generalized Functors
Dr. Partha Pratim DasInterra Systems (India) Pvt. Ltd.
Realizing Command Design Pattern in C++
![Page 2: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/2.jpg)
05-Mar-08 2
Agenda
• Design Patterns: Introduction
• Command Design Pattern
• How to realize Command Pattern in C++– Function Pointers– Functor– Generalized Functors
![Page 3: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/3.jpg)
05-Mar-08 3
Design Patterns
GoF BasicsGoF Basics
![Page 4: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/4.jpg)
05-Mar-08 4
What is a Design Pattern?
• A Design Pattern – describes a problem that occurs over and over
in software engineering – and then describes the solution in a
sufficiently generic manner as to be applicable in a wide variety of contexts.
![Page 5: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/5.jpg)
05-Mar-08 5
Essential Elements of a Design Pattern
1. Pattern Name: Descriptor for a design problem, its solutions, and their consequences.
2. Problem: Where to apply the pattern and its associated context.
3. Solution: Elements that make up the design, their relationships, responsibilities, and collaborations.
4. Consequences: Results and trade-offs in applying the pattern.
![Page 6: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/6.jpg)
05-Mar-08 6
Sample Design Patterns
Creational Structural Behavioral
Abstract Factory Composite Command
Singleton Proxy Iterator
Visitor
![Page 7: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/7.jpg)
05-Mar-08 7
Command Design Pattern
The World of DelegationThe World of Delegation
![Page 8: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/8.jpg)
05-Mar-08 8
“Check @ Diner” – A Command Pattern
• Customer places an Order with Waitress
• Waitress writes Order on check.
• Order is queued to Cook.
![Page 9: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/9.jpg)
05-Mar-08 9
“Compose & Send Mail” – A Command Pattern
• Sender composes a Mail with Word and presses “Send”
• Mail is queued on Outbox.
• SendMail thread checks the connection and send the Mails from Outbox.
![Page 10: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/10.jpg)
05-Mar-08 10
Command Pattern
• Intent– Encapsulate requests for service from an object
inside other objects to allow manipulation of the requests in various ways
![Page 11: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/11.jpg)
05-Mar-08 11
Command Pattern
• Motivation
![Page 12: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/12.jpg)
05-Mar-08 12
Command Pattern
• Motivation
![Page 13: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/13.jpg)
05-Mar-08 13
Command Pattern
• Applicability– The Command pattern can be used
• To implement a callback function capability
• To specify, queue, & execute requests at different times
• To support undo and change log operations
![Page 14: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/14.jpg)
05-Mar-08 14
Command Pattern
• Structure
• Interface Separation• Time Separation
![Page 15: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/15.jpg)
05-Mar-08 15
Command Pattern
• Participants– Command
• declares an interface for executing an operation.
– ConcreteCommand (PasteCommand, OpenCommand)• defines a binding between a Receiver object and an action.• implements Execute by invoking the corresponding operation(s) on
Receiver.
– Client (Application)• creates a ConcreteCommand object and sets its receiver.
– Invoker (MenuItem)• asks the command to carry out the request.
– Receiver (Document, Application)• knows how to perform the operations associated with carrying out a
request. Any class may serve as a Receiver.
![Page 16: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/16.jpg)
05-Mar-08 16
Command Pattern
• Collaborations
![Page 17: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/17.jpg)
05-Mar-08 17
Command Pattern
• Consequences– Command decouples the object that invokes the
operation from the one that knows how to perform it
– Commands are first-class objects. They can be manipulated and extended like any other object.
– Commands can be made into a composite command
![Page 18: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/18.jpg)
05-Mar-08 18
Command Pattern
Macro / Composite Command
![Page 19: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/19.jpg)
05-Mar-08 19
Command Pattern
• Implementation Issues– How intelligent should a command object be?– Dumb: Delegates the required action to a receiver
object– Smart: Implements everything itself without delegating
to a receiver object at all• Use Functor?
– Active Command: • A functor object usually implements the desired behavior itself
without delegation to another object. – Forwarding Command:
• A command object frequently delegates the desired behavior to another receiver object.
![Page 20: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/20.jpg)
05-Mar-08 20
Command Pattern: Request-in-Object
![Page 21: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/21.jpg)
05-Mar-08 21
Sample Command Pattern Usage
• Multi-level undo / redo – The program can keep a pair of stacks of
commands. • Transactional behavior
– Rollback for all-or-none operations– Installers / Databases. – Two-phase commit.
• Progress bars
![Page 22: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/22.jpg)
05-Mar-08 22
Sample Command Pattern Usage
• Wizards – What we see
• Several pages of configuration for a single action.• Action fires when the user clicks the "Finish" button.
– What we need• Separate user interface code from application code • Implement the wizard using a command object. • The command class contains no user interface code.
– How it works• Created when the wizard is first displayed. • Each wizard page stores its GUI changes in the command
object.• "Finish" simply triggers a call to execute().
![Page 23: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/23.jpg)
05-Mar-08 23
Sample Command Pattern Usage
![Page 24: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/24.jpg)
05-Mar-08 24
Sample Command Pattern Usage
![Page 25: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/25.jpg)
05-Mar-08 25
Sample Command Pattern Usage
![Page 26: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/26.jpg)
05-Mar-08 26
Sample Command Pattern Usage
![Page 27: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/27.jpg)
05-Mar-08 27
Sample Command Pattern Usage
![Page 28: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/28.jpg)
05-Mar-08 28
Sample Command Pattern Usage
• GUI buttons and menu items – In Swing and Borland Delphi programming, an Action
is a command object.
• Thread pools / Parallel Processing – Master/Worker pattern
• Macro recording• Command across Network
– Player actions in computer games.
• Mobile Code – Deliver a new behavior to remote locations
![Page 29: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/29.jpg)
05-Mar-08 29
How to Implement Command Pattern?
• Function Pointers?• Functors?• Generalized Functors?
![Page 30: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/30.jpg)
05-Mar-08 30
Function Pointers
RecapRecap
![Page 31: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/31.jpg)
05-Mar-08 31
Function Pointers
• Points to the address of a function– Ordinary C functions– Static C++ member functions– Non-static C++ member functions
• Points to a function with a specific signature– List of Calling Parameter Types– Return-Type – Calling Convention
![Page 32: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/32.jpg)
05-Mar-08 32
Function Pointers
• Operations– Assign an Address to a Function Pointer– Compare two Function Pointers– Call a Function using a Function Pointer– Pass a Function Pointer as an Argument– Return a Function Pointer– Arrays of Function Pointers
![Page 33: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/33.jpg)
05-Mar-08 33
Function Pointers
• Programming Techniques for– Replacing switch/if-statements, – Realizing user-defined late-binding or – Implementing callbacks.
![Page 34: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/34.jpg)
05-Mar-08 34
Function Pointers• Calculator with operators (+, –, *, /) // The four arithmetic operations float Plus (float a, float b) { return a+b; }float Minus (float a, float b) { return a-b; }float Multiply(float a, float b) { return a*b; }float Divide (float a, float b) { return a/b; }
// Solution with a switch-statement void Switch(float a, float b, char opCode) {
float result;switch(opCode) { // execute operation
case ’+’ : result = Plus (a, b); break;case ’-’ : result = Minus (a, b); break;case ’*’ : result = Multiply (a, b); break;case ’/’ : result = Divide (a, b); break;
} cout << "Switch: 2+5=" << result << endl; // display result}
![Page 35: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/35.jpg)
05-Mar-08 35
Function Pointers – Replace Switch / IF Statements
One of the four basic Arithmetic Operations - Addition
float Plus (float a, float b) { return a+b; }
void Switch_With_Function_Pointer (float a, float b, float (*pt2Func)(float, float))
{float result = pt2Func(a, b); cout << a << "+" << b << "=" << result << endl;
}
void main(){
Switch_With_Function_Pointer(2, 5, &Plus);}
![Page 36: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/36.jpg)
05-Mar-08 36
Function Pointers – Late Binding / Virtual Function
Late Binding is a C++ Feature
class A {public:
void f();virtual void g();
};
class B: public A {public:
void f();virtual void g();
};
void main() {A a;B b;A *p = &b;
a.f(); // A::f()a.g(); // A::g()p->f();// A::f()p->g();// B::g()
}
![Page 37: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/37.jpg)
05-Mar-08 37
Function Pointers – Callbacks
Quick Sort Implementation using callback in ‘qsort’
int CmpFunc(const void* a, const void* b) {int ret = (*(const int*)a > *(const int*) b)? 1:
(*(const int*)a == *(const int*) b)? 0: -1;return ret;
}
void main() {int field[10];for(int c=10;c>0;c--)
field[10-c]=c;qsort((void*) field, 10, sizeof(field[0]), CmpFunc);
}
![Page 38: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/38.jpg)
05-Mar-08 38
Function Pointers
• Issues– No value semantics– Weak type checking– Two function pointers having identical
signature are necessarily indistinguishable– No encapsulation for parameters
![Page 39: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/39.jpg)
05-Mar-08 39
Functors
Function Objects in C++Function Objects in C++
![Page 40: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/40.jpg)
05-Mar-08 40
Functors / Closures
• Smart Functions– Functors are functions with a state. – Functors encapsulate C / C++ function pointers
• Uses templates and • Engages polymorphism.
• Has its own Type– A class with
• zero or more private members to store the state and • an overloaded operator() to execute the function.
• Usually faster than ordinary Functions• Can be used to implement callbacks.
![Page 41: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/41.jpg)
05-Mar-08 41
Basic Functor
• Any class that overloads the function call operator:– void operator()();– int operator()(int, int);– double operator()(int, double);– ...
![Page 42: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/42.jpg)
05-Mar-08 42
Functors: Elementary Exampleint AdderFunction(int a, int b) {
return a + b;}
class AdderFunctor { public:
int operator()(int a, int b) {return a + b;
} };
void main() {int x = 5;int y = 7;int z = AdderFunction(x, y);
AdderFunctor aF;int w = aF(x, y);
}
![Page 43: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/43.jpg)
05-Mar-08 43
Functors: Examples from STL
• Fill a vector with random numbers– Function Pointer rand as Function Object
vector<int> V(100); generate(V.begin(), V.end(), rand);
![Page 44: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/44.jpg)
05-Mar-08 44
Functors: Examples from STL
• Sort a vector of double by magnitude– User-defined Functor less_mag
struct less_mag: public binary_function<double, double, bool> {
bool operator()(double x, double y) { return fabs(x) < fabs(y); }
};
vector<double> V; ... sort(V.begin(), V.end(), less_mag());
![Page 45: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/45.jpg)
05-Mar-08 45
Functors: Examples from STL
• Find the sum of elements in a vector– User-defined Functor adder with local statestruct adder: public
unary_function<double, void> { adder() : sum(0) {} double sum; void operator()(double x) { sum += x; }
};
vector<double> V; ... adder result =
for_each(V.begin(), V.end(), adder()); cout << "The sum is " << result.sum << endl;
![Page 46: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/46.jpg)
05-Mar-08 46
Generalized Functors
Basic NotionsBasic Notions
![Page 47: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/47.jpg)
05-Mar-08 47
Generalized Functors• Encapsulates any processing invocation• Accepts
– pointers to simple functions, – pointers to member functions, – functors, and – other generalized functors –with some or all of their respective arguments.
• Is typesafe – Never matches the wrong argument types to the wrong functions.
• Is an object with value semantics – Fully supports
• copying, • assignment, and • pass by value.
• A generalized functor can be copied freely and does not expose virtual member functions.
![Page 48: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/48.jpg)
05-Mar-08 48
Generalized Functors
• Implementation– Handle-Body (PIMPL) Idiom
class Functor { public:
void operator()(); // other member functions
private: // implementation goes hereFunctorImpl *pImpl_;
};
![Page 49: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/49.jpg)
05-Mar-08 49
Generalized Functors• Parameterized Return Values
template <typename ResultType> class Functor { public:
ResultType operator()(); // other member functions
private: // implementation
};
![Page 50: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/50.jpg)
05-Mar-08 50
Generalized Functors• No Argument (Generator)
• One Argument (Unary Function)
• Two Arguments (Binary Function)
template <typename ResultType> class Functor { ... };
template <typename ResultType, typename Parm1>
class Functor { ... };
template <typename ResultType, typename Parm1,typename Parm2>
class Functor { ... };
![Page 51: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/51.jpg)
05-Mar-08 51
Generalized Functors
• Variable List of Parameters– Variadic Function ellipses not allowed for templates
• Needs a set of Helper Templates• Needs representation for Collection of Types
int VarArgIntSum(int nParam, ...) {va_list va;va_start(va, nParam);for(int i = 0, sum = 0; i < nParam; i++) {
int& val = va_arg(va, int);sum += val;
}va_end(va);return sum;
}
![Page 52: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/52.jpg)
05-Mar-08 52
Helper Templates
• NullType– class NullType {};– Not an interesting type.– Marks the end of a typelist and to return "type
not found" information.
• EmptyType– struct EmptyType {};– "don't care" type for a template. – Legal to inherit from
![Page 53: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/53.jpg)
05-Mar-08 53
Typelist
• Typelists are a C++ tool for manipulating collections (list) of types.
• Typelist holds two types accessible through the inner names.– Head – Tail
![Page 54: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/54.jpg)
05-Mar-08 54
Typelist• Examples
• Generic Listtemplate <class T, class U>struct Typelist{
typedef T Head;typedef U Tail;
};
typedef Typelist<char, Typelist<signed char, unsigned char> > CharList;
typedef Typelist<char, Typelist<signed char,
Typelist<unsigned char, NullType> > > AllCharTypes;
![Page 55: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/55.jpg)
05-Mar-08 55
Typelist: Compute Length• Recursion Exit
• Recursion Descend Instantiationtemplate <class T, class U>struct Length< Typelist<T, U> >{
enum { value = 1 + Length<U>::value };};
template <class TList> struct Length;template <> struct Length<NullType>{
enum { value = 0 };};
![Page 56: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/56.jpg)
05-Mar-08 56
Typelist: Index a Type• Generic Template
• Recursion Exit
• Recursion Descend Instantiationtemplate <class Head, class Tail, unsigned int i>struct TypeAt<Typelist<Head, Tail>, i>{
typedef typename TypeAt<Tail, i - 1>::Result Result;};
template <class Head, class Tail>struct TypeAt<Typelist<Head, Tail>, 0>{
typedef Head Result;};
template <class Head, class Tail>struct TypeAt;
![Page 57: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/57.jpg)
05-Mar-08 57
Typelist: Arbitrary Number of Types
• Iterative Macro Definition
#define TYPELIST_1(T1) \Typelist<T1, NullType>
#define TYPELIST_2(T1, T2) \Typelist<T1, TYPELIST_1(T2) >
#define TYPELIST_3(T1, T2, T3) \Typelist<T1, TYPELIST_2(T2, T3) >
#define TYPELIST_4(T1, T2, T3, T4) \ Typelist<T1, TYPELIST_3(T2, T3, T4) >
//...//#define TYPELIST_50(...) ...
![Page 58: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/58.jpg)
05-Mar-08 58
Functor Implementation
template <typename R, class TList> class FunctorImpl;
template <typename R> class FunctorImpl<R, NullType> { public:
virtual R operator()() = 0; virtual FunctorImpl* Clone() const = 0; virtual ~FunctorImpl() {}
};
![Page 59: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/59.jpg)
05-Mar-08 59
Functor Implementation
template <typename R, typename P1> class FunctorImpl<R, TYPELIST_1(P1)> { public:
virtual R operator()(P1) = 0; virtual FunctorImpl* Clone() const = 0; virtual ~FunctorImpl() {}
};
template <typename R, typename P1, typename P2> class FunctorImpl<R, TYPELIST_2(P1, P2)> { public:
virtual R operator()(P1, P2) = 0; virtual FunctorImpl* Clone() const = 0; virtual ~FunctorImpl() {}
};
![Page 60: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/60.jpg)
05-Mar-08 60
The Functor
template <typename R, class TList> class Functor { public:
Functor(); Functor(const Functor&); Functor& operator=(const Functor&); explicit Functor(std::auto_ptr<Impl> spImpl);
... private:
// Handy type definition for the body type typedef FunctorImpl<R, TList> Impl; std::auto_ptr<Impl> spImpl_;
};
![Page 61: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/61.jpg)
05-Mar-08 61
The Functor: Forwarding Operatortemplate <typename R, class TList> class Functor { ... as above ... typedef TList ParmList; typedef typename
TypeAt<TList, 0, EmptyType>::Result Parm1; typedef typename
TypeAt<TList, 1, EmptyType>::Result Parm2;
public: R operator()()
{ return (*spImpl_)(); } R operator()(Parm1 p1)
{ return (*spImpl_)(p1); } R operator()(Parm1 p1, Parm2 p2)
{ return (*spImpl_)(p1, p2); } };
![Page 62: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/62.jpg)
05-Mar-08 62
Using Functor
// Define a Functor that accepts an int and // a double and returns a double. Functor<double, TYPELIST_2(int, double)> myFunctor;
// Invoke it. operator()(double, int) is generated. double result = myFunctor(4, 5.6);
// Wrong invocation. double result = myFunctor(); // error! // operator()() is invalid because // FunctorImpl<double, TYPELIST_2(int, double)> // does not define one.
![Page 63: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/63.jpg)
05-Mar-08 63
Using Functor
• Work by yourself
![Page 64: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/64.jpg)
05-Mar-08 64
References
• Chapter 5: Generalized Functors in Modern C++ Design: Generic Programming and Design Patterns Applied
– Andrei Alexandrescu• Chapter 22. Function Objects and Callbacks in
C++ Templates: The Complete Guide – David Vandevoorde & Nicolai M. Josuttis
• Chapter 8. STL Function Objects in The C++ Standard Library: A Tutorial and Reference
– Nicolai M. Josuttis• Effective C++ & More Effective C++
– Scott Meyers
![Page 65: Generalized Functors - Realizing Command Design Pattern in C++](https://reader034.vdocument.in/reader034/viewer/2022050808/554a0523b4c905557a8b538b/html5/thumbnails/65.jpg)
05-Mar-08 65
Thank You