Hi All,

Can you please help me to understand why the following code is behaving this way?
I think both outputs should be 1 ( 1 means const T), but its not!!

template <typename T>
struct IsConst{
	enum {isConst = 0};
};

template <typename T>
struct IsConst<const T>{
	enum {isConst = 1};
};

template <typename T>
void print(T val){
	cout << IsConst<T>::isConst << endl; //prints 0
}
int main() {

	const int x = 10;

	print(x); //why dynamic argument deduction deducting it as normal integer?

	cout << IsConst<const int>::isConst << endl; //prints 1

	return 0;
}

why dynamic argument deduction deducting it as normal integer?

Thanks in advance.

S.

Comments
I learned something here.. :)

why dynamic argument deduction deducting it as normal integer?

Top level CV qualifiers are stripped during the type deduction. That's actually expected behavior for template function parameters that aren't a pointer or reference.

As Narue said, the top-level cv-qualifier is discarded in function calls. This is simply because, like in your example, when you pass-by-value, the top-level cv-qualifier of the original value doesn't and shouldn't matter, because it is copied to the function anyways.

To fix the problem, simply make the parameter to print() a reference to T instead of T, as so:

#include <iostream>

template <typename T>
struct IsConst{
	enum {isConst = 0};
};

template <typename T>
struct IsConst<const T>{
	enum {isConst = 1};
};

template <typename T>
void print(T& val){ //notice the & here.
	std::cout << IsConst<T>::isConst << std::endl; //prints 1.. hurray!!
}
int main() {

	const int x = 10;

	print(x); //x will be implicitly transformed to 'const int&'

	std::cout << IsConst<const int>::isConst << std::endl; //prints 1

	return 0;
}

Edited 5 Years Ago by mike_2000_17: n/a

Thanks guys!!
It was helpful, I was looking in to boost code and found the solution.
But didn't know that const was getting stripped off.

This question has already been answered. Start a new discussion instead.