C ++ Template Specialization Problem

I need C ++ - a template that, given the type and object of this type, can make a decision based on whether the type is an integer or not, having access to the actual objects. I tried this

template <typename T, T &N>
struct C {
    enum { Value = 0 };
};

template <int &N>
struct C<int, N> {
    enum { Value = N };
};

but that will not work. Is there a way to achieve something like this?

Edit

What I was trying to achieve was something like this that would happen at compile time:

if (type is int) {
    return IntWrapper<int_value>
else {
    return type
}

In fact, you can pass pointers or object references in an instance of a template, for example:

struct X {
    static const int Value = 5;
};

template <X *x>
struct C {
    static const int Value = (*x).Value; 
};

X x;

std::cout << C<&x>::Value << std::endl; // prints 5

but, apparently, all this means initializing the template by type inference x, and xyou also need to declare it globally. Not to use what I'm trying to do, which, in my opinion, is impossible at the end of compilation.

+3
11

, , ++. , , , , .

+7

, , , . .

template <X *x>
struct C {
    static const int Value = (*x).Value; 
};

, (*x).Value , Value. , Value X X::Value. , ( ).

, :

Magic<T, someT>::type

, ::type T, T int, IntWrapper<someT> , T , , . "" , , . , , , ( , , ).

, , . , , .

+5

, ?

template<typename T>
void doSomething(const T& x)
{
    // ...
}
void doSomething(int x)
{
    // ...
}
+4

template <typename T> struct A
{
    enum { Value = false };
};
template <> struct A<int>
{
    enum { Value = true };
};

:


template <typename T> struct A
{
    T value_;
    A() : value() {}
    enum { is_int = false };
};
template <> struct A<int>
{
    int value_;
    explicit A( int v ) : value_( v ) {}
    enum { is_int = true };
};
+3

: enum {} -hack:

template<typename T, int val>
struct Test {
    static const int Value = 0;
};

template <int val>
struct Test<int, val> {
    static const int Value = val;
};


int main(int argc,char *argv[]) {
    const int v = Test<int,1>::Value;
}
+3

:

template<typename T, int val>
struct Test
{
    enum {Value = 0};
};

template <int val>
struct Test<int, val>
{
    enum {Value = val};
};




int main(int argc,char *argv[])
{
    int v = Test<int,1>::Value;
}  
+2

++, , , , , , .

, , . , , , , .

,

template < typename T, int >
class C {};

template< typename T, T >
class C {};

C<int, 5> , T, C<float, 5.> .

, ?

, int, , , 0 otherwhise, :

#include <limits>

template< typename T, int N >
class C {
    static const int Value = (std::numeric_limits<T>::is_integer) ? N : 0;
};
+2

- :

template <typename T, T N>
struct C {
    enum { Value = 0 };
};

template <int N>
struct C<int, N> {
    enum { Value = N };
};

, -.

0

Alexandrescu ++. , 2 , .

0

(, www.cplusplus.com):

// template specialization
#include <iostream>
using namespace std;

// class template:
template <class T>
class mycontainer {
    T element;
  public:
    mycontainer (T arg) {element=arg;}
    T increase () {return ++element;}
};

// class template specialization:
template <>
class mycontainer <char> {
    char element;
  public:
    mycontainer (char arg) {element=arg;}
    char uppercase ()
    {
      if ((element>='a')&&(element<='z'))
      element+='A'-'a';
      return element;
    }
};

int main () {
  mycontainer<int> myint (7);
  mycontainer<char> mychar ('j');
  cout << myint.increase() << endl;
  cout << mychar.uppercase() << endl;
  return 0;
}

char , . , , , , .

0

, , - , :

if (type is int) {
    return IntWrapper<int_value>
else {
    return type
}

, IntWrapper . IntWrapper, int?

Otherwise, it looks a bit like you are trying to create templates with data available only at run time.

0
source

Source: https://habr.com/ru/post/1709091/


All Articles