I've decided to create a stab at doing some library designing, starting with a clone_ptr class which allows for polymorphic types yet deep-copies (via clone() function of a template argument, cloner_type). Unfortunately, I've run into a minor stumbling block/design issue with the class.
In creating my usage case, I set up this:
std::vector< industry::clone_ptr< animal > > animals;
//fill animals
std::for_each( animals.begin() , animals.end() , std::mem_fun( &animal::noise ) );
Unfortunately, this dosn't work without an implicit cast to pointer, which I'd really rather not allow. Right now I'm banging up an industry::mem_fun_ptr which allows this behavior by accepting a templatized operator() argument rather than only normal pointers. For maximum flexibility, I'd like the functon returned (mem_fun_ptr_t) to use operator->* as per normal usage with pointers. However, I appear not to posess the knowledge to overload them :-).
According to at least
some sources, ->* can be overloaded, as a unary operator. I tried overloading it as one would operator->, as per so:
50 pointer_type operator->*( void ) {
return pointer;
}
53 const_pointer_type operator->*( void ) const {
return pointer;
}
However, I get these errors:
C:/eclipse/workspace/libindustry/industry/clone_ptr.hh:50: error: `value_t* industry::clone_ptr<value_t, cloner_t>::operator->*()' must take exactly one argument
C:/eclipse/workspace/libindustry/industry/clone_ptr.hh:53: error: `const value_t* industry::clone_ptr<value_t, cloner_t>::operator->*()' must take exactly one argument
C:/eclipse/workspace/libindustry/industry/clone_ptr.hh: In instantiation of `industry::clone_ptr<animal, industry::cloner<animal> >':
../main.cc:36: instantiated from here
Needless to say this has me rather confused - a unary operator should take zero arguments, right? So why is GCC (3.4.2) complaining about arguments, rather than, say, return types?
Currently, my usage case is completely working aside from this fact, and i can workaround like so:
for_each
( animals.begin()
, animals.end()
, compose1
( mem_fun( &animal::noise )
, mem_fun_ref( &clone_ptr< animal >::get )
)
);
But that's just plain ugly :-P.
Offtopic: Yes, I'm aware std::compose1 is an SGI extension - but I'm not using it (SGI's STL not installed) - I implemented industry::compose1, which is what's being used, outside of the std:: namespace, where it belongs ^_^.
Edit: It would appear that operator->* is actually a binary operator. I didn't believe
The MSDN, since it says that about operator-> as well, but considering that GCC dosn't choke on the function decleration when I do stuff like this:
template < typename argument_type >
argument_type operator->*( argument_type (value_type::*argument) ) {
return (pointer->*argument);
}
I'd say I'm on the right track - kind of maybe sorta.
This still dosn't work:
clone_ptr< animal > test_mutant;
test_mutant = test_duck;
void (animal::*function)( void ) const = &animal::noise;
(test_mutant->*function)(); //error: no match for 'operator->*' in 'test_mutant ->* function'
[Edited by - MaulingMonkey on May 26, 2005 1:35:38 PM]