2

I am trying to use std::function to achieve this (code does not compile, ofc):

template <typename Duration>
void operation1(int i)
{
    // do some chrono stuff
}

template <typename Duration>
void operation2(int i)
{
    // do other chrono stuff
}

void callFunc(const std::function<void(int)>& func, int i)
{
    func<std::chrono::hours>(i);
    func<std::chrono::minutes>(i);
    func<std::chrono::seconds>(i);
    func<std::chrono::milliseconds>(i);
}

int main()
{
    callFunc(operation1, 10);
    callFunc(operation2, 5);
}

The problem seems to be the fact that functions operations1 and operations2 are templatized and I don't know how to call them. If I remove the template, everything works ok.

I am open to other suggestions to use make the function callFunc a template if it works.

https://godbolt.org/z/cq5b1ozjP

Thank you

P.S. I know that calling callFunc(operation1<std::chrono::hours>, 10); works, but this does not help me, I am trying to get rid of duplicating code, otherwise I can delete the callFunc and use directly operation1 and operation2, like I am doing now...

Taw
  • 479
  • 3
  • 15

2 Answers2

2

It's similar to the question at here, but this question is slightly different because the template cannot be deduced from the argument type.

The template function cannot be passed or evaluated if it's not instantiated as the answer at the link.

So you should change your function to functor,

struct operation1 {
  template<typename Duration>
  void operator()(int i) {
    // do something
  }
};

and pass the functor to the caller.


template<typename Functor>
void callFunc(Functor func, int i)
{
  func.template operator()<std::chrono::hours>(i);
  func.template operator()<std::chrono::minutes>(i);
  func.template operator()<std::chrono::seconds>(i);
  func.template operator()<std::chrono::milliseconds>(i);
}

int main() {
  callFunc(operation1{}, 10);
}
김선달
  • 1,485
  • 9
  • 23
0

Just switch the bottom two lines to:

callFunc(opeartion1<int>, 10);  // int or any other type
callFunc(operation2<int>, 3);

Explanation, your function is not a concrete type until all template types are fully resolved, yielding a compile time error.

Moshe Rabaev
  • 1,892
  • 16
  • 31
  • if I do this, I would have a lot of duplicate code, that's what I want to avoid. thanks. – Taw Jun 23 '21 at 12:46