Michael Palm
Michael Palm

Reputation: 357

Specifying some template parameters

I want to write an own Vector-class and a function which calculates the cross product.

My Vector-class has the

template<class T, int dim, bool isRowVector>

T is the type of the entries, dim the dimension and isRowVector specifies whether the vector is a row or a column vector.

I overloaded some operators of Vector, particularly <<:

template <class T, int dim, bool isRowVec>
std::ostream& operator<<(std::ostream& os, Vector<T, dim, isRowVec>& vec) // <<
{
    os << "[" << vec[0];

    for(typename std::vector<T>::iterator it = vec.begin()+1; it != vec.end(); it++) {
        os << "," << *it;
    }

    os << "]";

    if(!isRowVec) { os << "^T"; }

    return os;
}

Now the function crossProduct should only apply on Vectors with dim = 3. So I specified the function like this:

template <class T, bool isRowVec>
Vector<T, 3, isRowVec> crossProduct (Vector<T, 3, isRowVec> a, Vector<T, 3, isRowVec> b) {
    T arr[3] = { a[1]*b[2]-a[2]*b[1], a[2]*b[0]-a[0]*b[2], a[0]*b[1]-a[1]*b[0] };
    Vector<T, 3, isRowVec> newVec(arr);
    return newVec;
}

omitting the dim parameter in the function template, since it does not have to be guessed or stated.

This doesn't seem to be a problem, since

Vector<float,3,true> a = crossProduct(f,g);

does not create a compile-error, where f and g are both

Vector<float,3,true>

But when I try to call

std::cout << crossProduct(f, g) << std::endl;

I get

error: no match for 'operator<<' (operand types are 'std::ostream {aka std::basic_ostream<char>}' and 'Vector<float, 3, true>')
  std::cout << crossProduct(f, g) << std::endl;
            ^

Any ideas?

Upvotes: 3

Views: 56

Answers (2)

P0W
P0W

Reputation: 47784

std::cout << crossProduct(f, g) << std::endl;
             |
             |
             +------Creates a temporary object (rvalue)

rvalues cannot bind to non-const references, so use const reference instead

template <class T, int dim, bool isRowVec>
std::ostream& operator<<(std::ostream& os, const Vector<T, dim, isRowVec>& vec) 
//                                         ~~~~~
{
   // ....
}

Upvotes: 2

Alan Stokes
Alan Stokes

Reputation: 18964

In your operator << you need const & vec rather than & vec.

You can't pass a temporary to a non-const reference, so you can't pass the result of the crossProduct call.

Upvotes: 0

Related Questions