views:

231

answers:

3

I'm refactoring a large amount of code where I have to add an extra parameter to a number of functions, which will always have a value of a member of that object. Something like

class MyClass
{
public:
   CMyObject A,B;

   void MyFunc(CMyObject &Object);
   // used to be void MyFunc();
};

Now, I'd actually like it to read

class MyClass
{
public:
   CMyObject A,B;

   void MyFunc(CMyObject &Object = A);
};

But I'm not allowed to have a default parameter that is a non-static member. I've read this similar question which suggest this isn't possible, but I'm wondering if there is any reasonable workaround. Reason being that 95% of the time the default parameter will be used, and thus using a default parameter would hugely reduce the amount of code I have to change. My best solution so far is something like this;

class MyClass
{
public:
   CMyObject A,B;

   void MyFunc(BOOL IsA = TRUE);
};

void MyClass::MyFunc(BOOL IsA)
{
    CMyObject &Object = A;
    if (!IsA)
        Object = &B;
}

This is less than elgant, but is there a better way of doing this that I'm missing?

Edit: FWIW, the reason for the extra parameter is to externalize some state related members from the object in question to aid multi-threading.

+8  A: 

How about :

class MyClass
{
public:
   CMyObject A,B;

   void MyFunc()
   { 
     MyFunc(A); 
   }
   void MyFunc(CMyObject &Object);
};

?

Benoît
Thanks Benoit, i knew there had to be a better way. Staring at the screen too long.
Shane MacLaughlin
You're welcome. Note that overloads aren't allowed in C# and Java, and this is the way to compensate. So I guess i haven't invented anything :-)
Benoît
@Benoît: I think you mean default parameters aren't allowed in C# and Java - they certainly allow overloads (and default parameters are apparently in C# 4.0)
Michael Burr
Yes sorry that's exactly what i meant, of course :-)
Benoît
A: 

Another way:

class MyClass
{
public:
   MyObject A,B;

   void MyFunc(MyObject MyClass::*myObject = &MyClass::A) {
       MyObject& obj = *(this->*myObject);
   }
};

This makes it even impossible to pass in an MyObject member from another MyClass instance. Your three valid options to call MyFunc are .MyFunc(), .MyFunc(&MyClass::A) and .MyFunc(&MyClass::B)

MSalters
A: 

Use pointers instead.

class MyClass {
    public:
    CMyObject A,B;

    void MyFunc(CMyObject* Object = NULL) {
        if(!Object) Object = &A;
        ...
    }
 };
Helltone