I have struct Opers
with some arithmetic operations: mult()
, div()
, mod()
.
And I need to specialize template for certain values of n
. Here is example for Opers<1>
.
But, also I want to do specialization for n
that are powers of 2 ( n = 2,4,8,16, ...) – in this case I can optimize operations mult()
and div()
(using bitwise shift left or right).
#include <iostream>
using namespace std;
template<int n> struct Opers {
int mult(int x){
return n*x;
}
int div(int x){
return x / n;
}
int mod(int x){
return x % n;
}
};
template<> struct Opers<1> {
int mult(int x){
return 1;
}
int div(int x){
return x;
}
int mod(int x){
return 0;
}
};
int main() {
Opers<1> el2;
cout << el2.mult(3) <<endl;
}
I'm looking for construction like
template<> struct Opers<isPowerOfTwo()>
int mult(int x){
// do smth
}
Is it possible or what manual should I read?
UPD. Using C++11 is allowed, and even would be better.
There are ways to restrict the types you can use inside a template you write by using specific typedefs inside your template. This will ensure that the compilation of the template specialisation for a type that does not include that particular typedef will fail, so you can selectively support/not support certain types.
Template in C++is a feature. We write code once and use it for any data type including user defined data types.
The act of creating a new definition of a function, class, or member of a class from a template declaration and one or more template arguments is called template instantiation. The definition created from a template instantiation is called a specialization.
An explicit specialization of a function template is inline only if it is declared with the inline specifier (or defined as deleted), it doesn't matter if the primary template is inline.
In C++11, you could do it this way. First of all, change your primary template so that it accepts a second, dummy parameter:
template<int n, typename = void>
struct Opers
{
// ...
};
Then, write a constexpr
function that determines whether an integer is a power of 2:
constexpr bool is_power_of_two(int x)
{
return (x == 1) || ((x % 2 == 0) && is_power_of_two(x / 2));
}
Finally, use SFINAE to enable or disable the specialization based on the result of your constexpr
function:
#include <type_traits>
template<int n>
struct Opers<n, typename std::enable_if<is_power_of_two(n)>::type>
{
// ...
};
template <int N, typename = void>
struct Operations
{
// ....
};
template <int N, typename = std::enable_if<(N & (N - 1))>::type>
struct Operations
{
// ....
};
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With