views:

103

answers:

4

I have a vector class with a properly overloaded Vect*float operator and am trying to create the global/non-member float*Vect operator as follows: (Note this is a heavily edited sample)

class Vect
{
    public:
        Vect::Vect(const float p_x, const float p_y, const float p_z, const float p_w);
        Vect operator*(const float p_sclr) const;
    private:
        float x;
        float y;
        float z;
        float w;
};
Vect::Vect(const float p_x, const float p_y, const float p_z, const float p_w) {
    x = p_x;
    y = p_y;
    z = p_z;
    w = p_w;
}
Vect Vect::operator*(const float p_sclr) const {
    return Vect( (x * p_sclr), (y * p_sclr), (z * p_sclr), 1); // reset w to 1
}
//Problem Non-MemberOperator
Vect operator*(const float p_sclr, const Vect& p_vect);
Vect operator*(const float p_sclr, const Vect& p_vect) {
    return p_vect * p_sclr;
}

But when I go to test the operator with the call:

Vect A(2.0f, 3.0f, 4.0f, 5.0f);
float s = 5.0f;
Vect C, D;
C = A * s; // Fine
D = s * A; // Error as below

I receive the following compile error:

error C2678: binary '*' : no operator found which takes a left-hand operand of type 'float' (or there is no acceptable conversion)

Can anyone provide insight to why this happens? The MS documentation is available at http://msdn.microsoft.com/en-us/library/ys0bw32s(v=VS.90).aspx and isn't very helpful Visual Studio 2008. This is the only compile error or warning I receive.

+3  A: 

You still havn't posted a complete example. I can compile the following code without any problems:

class vect
{
    float coeffs[4];
public:
    vect()
    {
        for (int k=0; k<4; ++k)
            coeffs[k] = 0;
    }

    vect(float x, float y, float z, float w)
    {
        coeffs[0] = x;
        coeffs[1] = y;
        coeffs[2] = z;
        coeffs[3] = w;
    }

    vect operator*(float scalar) const
    {
        return vect(
            scalar*coeffs[0],
            scalar*coeffs[1],
            scalar*coeffs[2],
            scalar*coeffs[3] );
    }
};

vect operator*(float scalar, vect const& x)
{
    return x*scalar;
}

void test()
{
    vect a (2,3,4,5);
    float s = 5;
    vect c, d;
    c = a * s;
    d = s * a;
}

So, the problem must lie somewhere else.

sellibitze
+1. You're quick!
SauceMaster
+3  A: 

I also can compile the code without any problems (like sellibitze, who beat me to it!)

Here's the code I used:

//main.cpp

#include <iostream>
using namespace std;


class Vect
{

public:
    float x,y,z,w;
Vect(const float p_x, const float p_y, const float p_z, const float p_w) {
   x = p_x;
   y = p_y;
   z = p_z;
   w = p_w;
}
Vect()
{
    x=y=z=w=0;
}

Vect operator*(const float p_sclr) const {
   return Vect( (x * p_sclr), (y * p_sclr), (z * p_sclr), 1); // reset w to 1
}


};

Vect operator*(const float p_sclr, const Vect& p_vect) {
   return p_vect * p_sclr;
}


int main()
{
    Vect A(2.0f, 3.0f, 4.0f, 5.0f);
    float s = 5.0f;
    Vect C, D;
    C = A * s; // Fine
    D = s * A; // Error as below
    cout << D.x << endl;
    return 0;
}

Edit: Like sellibitze suggests, the problem may lie elsewhere. Is the error you're listing the ONLY error your compiler is giving you? Also, what version of Visual Studio are you running?

SauceMaster
+1  A: 

Looks like 2 beat me to it, but it worked for me too - built and ran fine (VS2010, Win32 console project):

class Vect
{
public:
    float x,y,z,w;
    Vect::Vect(){}
    Vect::Vect(const float p_x, const float p_y, const float p_z, const float p_w) 
    {   
        x = p_x;   
        y = p_y;   
        z = p_z;   
        w = p_w;
    }
    Vect Vect::operator*(const float p_sclr) const 
    {   
        return Vect( (x * p_sclr), (y * p_sclr), (z * p_sclr), 1); // reset w to 1
    }
};

Vect operator*(const float p_sclr, const Vect& p_vect) {   return p_vect * p_sclr;}

int _tmain(int argc, _TCHAR* argv[])
{
    Vect a (2,3,4,5);
    float s = 5;
    Vect c, d;
    c = a * s;
    d = s * a;

}
PatrickV
A: 

The final solution was to go with a friend function because the variables were in p_vect were private:

//class definition
friend Vect operator*(const float scale, const Vect& p_vect);

//function
Vect operator*(const float p_sclr, const Vect& p_vect) {
   return Vect( (p_vect.x * p_sclr), (p_vect.y * p_sclr), (p_vect.z * p_sclr), 1.0f);
}
Kevin Stich
How does it solve the original problem? Why do you think a slightly different implementation of operator*(float,Vect) suddenly makes the compiler look up the operator differently? Next time, just provide a complete example including the real error message.
sellibitze
It solves the original problem because the compiler sees the function exists now. Not sure why it wasn't in the first place. Posting a complete example would have meant copying in the 600+ lines of code for the files and I could not duplicate the issue with another small, from-scratch test.
Kevin Stich