Tomasz Kasperczyk
Tomasz Kasperczyk

Reputation: 2093

Overloading functions without rewriting their whole definition

See the following example:

class bar{
    private:
        unsigned _timeout;
    public:
        bool foo(unsigned arg);
        bool foo(unsigned arg, unsigned timeout);
};

bool bar::foo(unsigned arg){
    /*50 lines of code*/
    if (_timeout > 4)
       //...
}

bool bar::foo(unsigned arg, unsigned timeout){
    /*50 lines of code*/
    if (timeout > 4)
       //...
}

As you can see these functions differ only in one line - first of them is using the private member _timeout, and the second one checks the variable timeout passed as the argument. The problem here is, that I have to rewrite the whole ~50 lines of code in order to overload this function. Is there any workaround?

Upvotes: 1

Views: 643

Answers (3)

Christian Hackl
Christian Hackl

Reputation: 27528

Implement both functions in terms of two other, private ones:

class bar{
    private:
        unsigned _timeout;

        void fooImplBegin(unsigned arg);
        bool fooImplEnd(unsigned arg);
    public:
        bool foo(unsigned arg);
        bool foo(unsigned arg, unsigned timeout);
};

void bar::fooImplBegin(unsigned arg) {
    /*50 lines of code */
}

bool bar::fooImplEnd(unsigned arg) {
    /* more lines of code, returning something */
}

bool bar::foo(unsigned arg){
    fooImplBegin(arg);
    if (_timeout > 4)
       //...
    return fooImplEnd(arg);
}

bool bar::foo(unsigned arg, unsigned timeout){
    fooImplBegin(arg);
    if (timeout > 4)
       //...
    return fooImplEnd(arg);
}

Upvotes: 0

Drew McGowen
Drew McGowen

Reputation: 11706

Two choices: either extract common functionality into its own function (refactoring), or have one call the other.

In your case, you can define the first overload like this:

bool bar::foo(unsigned arg) {
    return foo(arg, _timeout);
}

In general, refactoring is also a good approach:

void bar::foo_inner(unsigned arg) { // or however it should be declared
    // 50 lines of code
}

bool bar::foo(unsigned arg) {
    foo_inner(arg);
    if (_timeout < 4)
        ...
}

bool bar::foo(unsigned arg, unsigned timeout) {
    foo_inner(arg);
    if (timeout < 4)
        ...
}

Upvotes: 3

Kerrek SB
Kerrek SB

Reputation: 477040

How about this:

bool bar::foo(unsigned arg)
{
    return foo(arg, _timeout);
}

Upvotes: 2

Related Questions