user485611
user485611

Reputation: 23

How to define function with different templates as input

I am completely new to C++ (and Stack Overflow), so please bear with me. I am trying to create two templates and a function that takes inputs from both templates.

I have tried to make some sample code that resembles my code, and which reproduces the error. Basically I have two templates Dog and Cat, and want to create an operator function which takes an instance of Dog and Cat respectively, but I am really struggling with how to write the function header. After having spent a lot of time reading Stack Overflow posts, I have thrown in keywords 'template' and 'typename' in an attempt to make it work, but I keep getting errors. Currently the error is

candidate template ignored: couldn't infer template argument 'T'

template <class T> class Dog
{
private:
    int size;

public:
  Dog(int size1)
    {
        size = size1;
    }
};

template <class T> class Cat
{
private:
    int size;

public:
    Cat(int size1)
    {
        size = size1;
    }

};

template <class T> // What to write here?
typename Cat<T>::template Cat<T> operator*(typename Dog<T>::template Dog<T> m,typename Cat<T>::template Cat<T> v)
{
    Cat<int> return_cat(1);
    return return_cat;
}

int main(int argc, char* argv[]) 
{

    Cat<double>::Cat<double> new_cat(2);

    Dog<double>::Dog<double> new_dog(4);

    Cat<double>::Cat<double> result = new_dog*new_cat; // ERROR couldn't infer template argument 'T'

    return 0;
}

My question is: How should I define the function header for the operator* function to avoid any errors?

Upvotes: 2

Views: 73

Answers (3)

Valeca
Valeca

Reputation: 122

To simplify it a little bit for easier "reading" and not "mixing" dogs with cats :), you can play with this overload

template <class T>
class Animal
{
  private:
    T size;
  public:
  Animal(T size1) {
    size = size1;
  }
  T getSize() {
     return size;
}
Animal<T> operator*(Animal<T> animal1)
{
  T a = animal1.getSize();
  T b = this->getSize();
  Animal<T> animal = Animal<T>(a*b);
  return animal;
 }

};

int main(int argc, char* argv[]) {

Animal<double> cat(2);
Animal<double> dog(4);
Animal<double> result( dog*cat );
return 0;

}

Upvotes: 0

user10957435
user10957435

Reputation:

I'm not sure what your intended use of operator*() is, but generally it will look something like this:

template <class T> 
Cat<T> operator*(Dog<T> m, Cat<T> v)

This allows a cat and dog to be multiplied if their template class is the same.

If they are not the same (that is, cat and dog have different types), you will want something like this instead:

template <class T1, class T2> 
Cat<T2> operator*(Dog<T1> m, Cat<T2> v)

This allows for cat and dog to have different types and be multiplied together.

Upvotes: 0

Nico Schertler
Nico Schertler

Reputation: 32587

I am not sure what you were trying to do with all the scope operators. You don't need them. Simply use the proper types. I have added const references because it looked reasonable for this scenario. They are not strictly required.

template <class T>
Cat<T> operator*(const Dog<T>& m, const Cat<T>& v)
{
    Cat<T> return_cat(1);
    return return_cat;
}

int main(int argc, char* argv[])
{    
    Cat<double> new_cat(2);    
    Dog<double> new_dog(4);    
    Cat<double> result = new_dog * new_cat;    
    return 0;
}

Upvotes: 2

Related Questions