2

I would like to have a concept for the

struct creatorclass {
  template<typename T>
  int fct(T val)
  {
    return 42;
  }
};

What I would like is a concept that checks for the existence of a function fct without specifying the template parameter. That is want to have

template<typename U>
concept CREATOR=requires(U val) {
  val.fct;
};

I think that this is not possible since a concept needs to be evaluated and so compiled. This cannot be done without knowing the class T. Am I correct?

Note: Specifying a concept for a type that has a member function template using Concepts Lite also says this is not possible but this is for concept-lite six years ago before the C++20 standard.

  • 1
    Yes, it's impossible. – HolyBlackCat Apr 14 '21 at 13:26
  • 2
    Not clear what do you exactly want... do you want to verify the existence of a generic function (zero or more arguments; template or not)? Or the existence of a template function receiving exactly one argument (of a template type)? Or what else? – max66 Apr 14 '21 at 13:30
  • This depends on the signature of the `fct` member function. To check for it's existence you need to know how to call it, or how many parameters it takes and what types those parameters are. – super Apr 14 '21 at 13:34
  • because templates may be specialized or constrained, you would need to be more specific in your concept about how you would call `fct` (e.g., what type?) – AndyG Apr 14 '21 at 13:35
  • I don't think this question was closed with an appropriate dupe target. – dfrib Apr 14 '21 at 13:40
  • @dfrib: Why not? They're all the same question at the bottom: user wants to write a constraint that involves a type that is not part of the constraint. That's not a thing constraints can do. – Nicol Bolas Apr 14 '21 at 13:43
  • @NicolBolas In this particular case, I would say that the existing answer to this Q actually provides an answer (to _"a concept that checks for the existence of a function fct without specifying the template parameter [...] without **knowing the class** `T`"_), using the same approach as e.g. [in this Q&A](https://stackoverflow.com/questions/65957179/). None of the answers in the linked to dupes asks about restraining member function templates, nor do the answers show that you _can_ (through the somewhat exotic `.template ...` keyword usage). I would say the threads are "related", not dupes. – dfrib Apr 14 '21 at 13:48
  • ... but let's see what the OP says; my interpretation is that "without _specifying_ the template parameter" here is a confusion, and that the root question is "without _knowing_ the class `T`". – dfrib Apr 14 '21 at 13:50
  • @dfrib: The OP said, "*What I would like is a concept that checks for the existence of a function fct without specifying the template parameter.*" – Nicol Bolas Apr 14 '21 at 13:50
  • @dfrib: "*that the root is 'without knowing the class T'*" If that's without the *concept* knowing about the `T`, then it's the same problem. The issue is that the concept needs to know that there is a template parameter and to fill one in, so if it could be any type, the concept needs to have that be part of *its* template parameters. – Nicol Bolas Apr 14 '21 at 13:52
  • @NicolBolas I _think_ the OP (given the duality in his statements) is after what the existing answer has provided, which indeed _specifies_ the template parameter, but my interpretation is that this sentence is a red herring in the (not entirely well-specified question). _"Knowing the class `T`"_ is not using normative wording and could be layman wording for _"without specifying specific template arguments for the template parameter `T`"_. But only the OP knows, so let's see if he can get back and either update the question (remove duping?) or is happy about the dupe targets. – dfrib Apr 14 '21 at 13:57
  • ... Or, what are the OP's answers to @max66's questions above. – dfrib Apr 14 '21 at 14:00

1 Answers1

3

As far as I am aware, it is not possible to test for a template member function without evaluating any of the template parameters.

That said, if you have an idea of what the classification of inputs are allowed to be -- such as if a function can only be evaluated with integral-values or something like this -- then you can test it with an explicit instantiation which may be 'good enough' for whatever your purposes are:

template<typename U>
concept CREATOR=requires(U val) {
  // Checks that 'val' has a 'fct' function template that works with integers
  val.template fct<int>(5); 
};

Live Example

In most cases, however, its generally more useful for a concept to be defined around the complete atomic definition required to fulfill its contract -- at which point its generally better to punt this evaluation off to a template argument as well:

template <typename T, typename U>
concept fnc_evaluatable = requires(T val, U in) {
    val.template fct<U>(in);
};

And then use this in greater compositions.

At this point, the state of fnc being a template also becomes less important than the state of it having a member function call fct that is callable by a U -- and can likely be simplified to just:

template <typename T, typename U>
concept fnc_evaluatable = requires(T val, U in) {
    val.fct(in);
};
Human-Compiler
  • 11,022
  • 1
  • 32
  • 59