casa  5.7.0-16
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
functor.h
Go to the documentation of this file.
1 //# functor.h: declaration & definition of functors + args
2 //#
3 //# Copyright (C) 2011
4 //# Associated Universities, Inc. Washington DC, USA.
5 //#
6 //# This library is free software; you can redistribute it and/or modify it
7 //# under the terms of the GNU Library General Public License as published by
8 //# the Free Software Foundation; either version 2 of the License, or (at your
9 //# option) any later version.
10 //#
11 //# This library is distributed in the hope that it will be useful, but WITHOUT
12 //# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 //# FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public
14 //# License for more details.
15 //#
16 //# You should have received a copy of the GNU Library General Public License
17 //# along with this library; if not, write to the Free Software Foundation,
18 //# Inc., 675 Massachusetts Ave, Cambridge, MA 02139, USA.
19 //#
20 //# Correspondence concerning AIPS++ should be addressed as follows:
21 //# Internet email: aips2-request@nrao.edu.
22 //# Postal address: AIPS++ Project Office
23 //# National Radio Astronomy Observatory
24 //# 520 Edgemont Road
25 //# Charlottesville, VA 22903-2475 USA
26 //#
27 //# $Id$
28 
29 #ifndef __casadbus_functor_h__
30 #define __casadbus_functor_h__
31 #include <casadbus/types/ptr.h>
32 #include <string>
33 #include <stdexcept>
34 
35 namespace casa {
36  namespace functor {
37 
38  class args {
39  public:
40  virtual ~args( ) { }
41  };
42 
43  template<class T1> class args01 : public args {
44  public:
45  args01( T1 v1 ) : a1(v1) { }
46  T1 one( ) { return a1; }
47  private:
48  T1 a1;
49  };
50 
51  template<class T1, class T2> class args02 : public args {
52  public:
53  args02( T1 v1, T2 v2 ) : a1(v1), a2(v2) { }
54  T1 one( ) { return a1; }
55  T2 two( ) { return a2; }
56  private:
57  T1 a1;
58  T2 a2;
59  };
60 
61  template<class T1, class T2, class T3> class args03 : public args {
62  public:
63  args03( T1 v1, T2 v2, T3 v3 ) : a1(v1), a2(v2), a3(v3) { }
64  T1 one( ) { return a1; }
65  T2 two( ) { return a2; }
66  T3 three( ) { return a3; }
67  private:
68  T1 a1;
69  T2 a2;
70  T3 a3;
71  };
72 
73  template<class T1, class T2, class T3, class T4> class args04 : public args {
74  public:
75  args04( T1 v1, T2 v2, T3 v3, T4 v4 ) : a1(v1), a2(v2), a3(v3), a4(v4) { }
76  T1 one( ) { return a1; }
77  T2 two( ) { return a2; }
78  T3 three( ) { return a3; }
79  T4 four( ) { return a4; }
80  private:
81  T1 a1;
82  T2 a2;
83  T3 a3;
84  T4 a4;
85  };
86 
87 
88  class invocation_exception : public std::runtime_error {
89  public:
90  invocation_exception( ) : std::runtime_error( "functor/argument mismatch" ) { }
91  };
92 
93  class f_ {
94  public:
95  f_( ) { }
96  virtual void invoke( args *a ) = 0;
97  virtual ~f_( ) { }
98  };
99 
100  class f {
101  public:
102  f( const f &other ) : ptr(other.ptr) { }
103  void operator()( args *a ) { ptr->invoke( a ); }
104  void operator()( args &a ) { ptr->invoke( &a ); }
105  std::string state( ) const { return ptr.state( ); }
106  virtual ~f( ) { }
107  private:
108  f( );
109  f( f_ *p ) : ptr(p) { }
110  void operator=(const f &);
112 
113  template <class C> friend f make( C *o, void (C::*i)( ) );
114  template <class C, class P1> friend f make( C *o, void (C::*i)(P1) );
115  template <class C, class P1, class P2> friend f make( C *o, void (C::*i)(P1,P2) );
116  template <class C, class P1, class P2, class P3> friend f make( C *o, void (C::*i)(P1,P2,P3) );
117  template <class C, class P1, class P2, class P3, class P4> friend f make( C *o, void (C::*i)(P1,P2,P3,P4) );
118  };
119 
120 
121  template <class C> class f00 : public f_ {
122  public:
123  f00( C *o, void (C::*i)( ) ) : obj(o), impl(i) { }
124  void invoke( ) { (*obj.*impl)( ); }
125  void invoke( args *ga ) { (*this)( ); }
126  private:
127  C *obj;
128  void (C::*impl)( );
129  };
130 
131  template <class C, class P1> class f01 : public f_ {
132  public:
133  f01( C *o, void (C::*i)(P1) ) : obj(o), impl(i) { }
134  void invoke( P1 a1 ) { (*obj.*impl)(a1); }
135  void invoke( args *ga ) {
136  args01<P1> *a = dynamic_cast<args01<P1>*>(ga);
137  if ( a ) { (*this)(a->one()); }
138  else { throw invocation_exception( ); }
139  }
140  private:
141  C *obj;
142  void (C::*impl)(P1);
143  };
144 
145  template <class C, class P1, class P2> class f02 : public f_ {
146  public:
147  f02( C *o, void (C::*i)(P1,P2) ) : obj(o), impl(i) { }
148  void invoke( P1 a1, P2 a2 ) { (*obj.*impl)(a1,a2); }
149  void invoke( args *ga ) {
150  args02<P1,P2> *a = dynamic_cast<args02<P1,P2>*>(ga);
151  if ( a ) { invoke(a->one(),a->two()); }
152  else { throw invocation_exception( ); }
153  }
154  private:
155  C *obj;
156  void (C::*impl)(P1,P2);
157  };
158 
159  template <class C, class P1, class P2, class P3> class f03 : public f_ {
160  public:
161  f03( C *o, void (C::*i)(P1,P2,P3) ) : obj(o), impl(i) { }
162  void invoke( P1 a1, P2 a2, P3 a3 ) { (*obj.*impl)(a1,a2,a3); }
163  void invoke( args *ga ) {
164  args03<P1,P2,P3> *a = dynamic_cast<args03<P1,P2,P3>*>(ga);
165  if ( a ) { (*this)(a->one(),a->two(),a->three()); }
166  else { throw invocation_exception( ); }
167  }
168  private:
169  C *obj;
170  void (C::*impl)(P1,P2,P3);
171  };
172 
173  template <class C, class P1, class P2, class P3, class P4> class f04 : public f_ {
174  public:
175  f04( C *o, void (C::*i)(P1,P2,P3,P4) ) : obj(o), impl(i) { }
176  void invoke( P1 a1, P2 a2, P3 a3, P4 a4 ) { (*obj.*impl)(a1,a2,a3,a4); }
177  void invoke( args *ga ) {
178  args04<P1,P2,P3,P4> *a = dynamic_cast<args04<P1,P2,P3,P4>*>(ga);
179  if ( a ) { (*this)(a->one(),a->two(),a->three(),a->four()); }
180  else { throw invocation_exception( ); }
181  }
182  private:
183  C *obj;
184  void (C::*impl)(P1,P2,P3,P4);
185  };
186 
187  template <class C> f make( C *o, void (C::*i)( ) )
188  { return f(new functor::f00<C>( o, i )); }
189  template <class C, class P1> f make( C *o, void (C::*i)(P1) )
190  { return f(new functor::f01<C,P1>( o, i )); }
191  template <class C, class P1, class P2> f make( C *o, void (C::*i)(P1,P2) )
192  { return f(new functor::f02<C,P1,P2>( o, i )); }
193  template <class C, class P1, class P2, class P3> f make( C *o, void (C::*i)(P1,P2,P3) )
194  { return f(new functor::f03<C,P1,P2,P3>( o, i )); }
195  template <class C, class P1, class P2, class P3, class P4> f make( C *o, void (C::*i)(P1,P2,P3,P4) )
196  { return f(new functor::f04<C,P1,P2,P3,P4>( o, i )); }
197 
198  }
199 }
200 
201 #endif
void invoke(P1 a1)
Definition: functor.h:134
void invoke(args *ga)
Definition: functor.h:135
void(C::* impl)(P1)
Definition: functor.h:142
void invoke(args *ga)
Definition: functor.h:163
void invoke(P1 a1, P2 a2, P3 a3, P4 a4)
Definition: functor.h:176
f04(C *o, void(C::*i)(P1, P2, P3, P4))
Definition: functor.h:175
virtual ~f()
Definition: functor.h:106
void operator()(args &a)
Definition: functor.h:104
void invoke(P1 a1, P2 a2)
Definition: functor.h:148
virtual ~f_()
Definition: functor.h:97
void(C::* impl)(P1, P2)
Definition: functor.h:156
args04(T1 v1, T2 v2, T3 v3, T4 v4)
Definition: functor.h:75
f00(C *o, void(C::*i)())
Definition: functor.h:123
void invoke(args *ga)
Definition: functor.h:177
friend f make(C *o, void(C::*i)())
Definition: functor.h:187
std::string state() const
Definition: functor.h:105
args02(T1 v1, T2 v2)
Definition: functor.h:53
f02(C *o, void(C::*i)(P1, P2))
Definition: functor.h:147
void invoke(args *ga)
Definition: functor.h:125
f01(C *o, void(C::*i)(P1))
Definition: functor.h:133
void(C::* impl)()
Definition: functor.h:128
f(const f &other)
Definition: functor.h:102
args03(T1 v1, T2 v2, T3 v3)
Definition: functor.h:63
memory::cptr< f_ > ptr
Definition: functor.h:111
void(C::* impl)(P1, P2, P3)
Definition: functor.h:170
void operator=(const f &)
void invoke(args *ga)
Definition: functor.h:149
void invoke(P1 a1, P2 a2, P3 a3)
Definition: functor.h:162
f03(C *o, void(C::*i)(P1, P2, P3))
Definition: functor.h:161
void operator()(args *a)
Definition: functor.h:103
virtual ~args()
Definition: functor.h:40
void(C::* impl)(P1, P2, P3, P4)
Definition: functor.h:184
f make(C *o, void(C::*i)())
Definition: functor.h:187
virtual void invoke(args *a)=0