 |
C++Talk.NET C++ language newsgroups
|
| View previous topic :: View next topic |
| Author |
Message |
Bart Samwel Guest
|
Posted: Mon Apr 25, 2005 4:18 pm Post subject: rvalues and template argument deduction |
|
|
NOTE: This posting is the result of a discussion on comp.lang.c++,
subject "Template argument deduction on integer literals".
Please consider this snippet:
template<typename A>
void foo(A&)
{
}
int main()
{
foo(10);
}
What happens here is that the type deduced for A is "int", after which
compilation fails because one cannot bind an rvalue to a reference that
is not to "const". This happens with all compilers that I've tried
(Comeau, g++ 3.3, MSVC++ 7.1). However, IMHO the compiler *should* be
able to see that the value passed is an rvalue, and it *should* know
that if it selects "int" here, that compilation will subsequently fail.
Quoting the standard [temp.deduct.call], the compiler can apply the
following alternative deduction:
"If the original P is a reference type, the deduced A (i.e., the type
referred to by the reference) can be more cv-qualified than A."
In the snippet above, as I read the standard, P = "int&", so the
deduced "A" is allowed to be "int" but also "const int". However, the
standard also says here that:
"These alternatives are considered only if type deduction would
otherwise fail."
So, apparently type deduction doesn't fail in the situation in the
snippet above. But the subsequent call *always* fails, and this should
be perfectly clear to the compiler! So, my question is, might it be a
good idea to change the standard to include the rvalue-ness of the
passed value in the equation, and to always deduce a top-level "const"
qualifier whenever the value whose type is "A" is an rvalue and "P" is
a reference type?
--Bart
P.S.: For those of you who want to know why I would want this to work
this way, please read the discussion in comp.lang.c++. I explain the
situation I'm dealing with in some length there.
The abstract: I'm trying to build a "generic pass-through" function
which passes on its arguments to another, unknown function (in this
case, a constructor for a type which is also a template parameter), and
which passes the arguments through completely unchanged, so that the
same function overload is selected as when the function would have been
called directly, preserving both reference-ness and constness for all
arguments. We provide overloads for 0 to 20 arguments for the
pass-through function, so providing overloads for all combinations of
const/non-const argument types is not an option; this would yield 2**20
overloads for the 20-argument version alone!
---
[ comp.std.c++ is moderated. To submit articles, try just posting with ]
[ your news-reader. If that fails, use mailto:std-c++@ncar.ucar.edu ]
[ --- Please see the FAQ before posting. --- ]
[ FAQ: http://www.jamesd.demon.co.uk/csc/faq.html ]
|
|
| Back to top |
|
 |
Howard Hinnant Guest
|
Posted: Mon Apr 25, 2005 4:59 pm Post subject: Re: rvalues and template argument deduction |
|
|
In article <1114339382.885440.25740 (AT) z14g2000cwz (DOT) googlegroups.com>,
"Bart Samwel" <bsamwel (AT) gmail (DOT) com> wrote:
| Quote: | The abstract: I'm trying to build a "generic pass-through" function
which passes on its arguments to another, unknown function (in this
case, a constructor for a type which is also a template parameter), and
which passes the arguments through completely unchanged, so that the
same function overload is selected as when the function would have been
called directly, preserving both reference-ness and constness for all
arguments. We provide overloads for 0 to 20 arguments for the
pass-through function, so providing overloads for all combinations of
const/non-const argument types is not an option; this would yield 2**20
overloads for the 20-argument version alone!
|
You are in good company. The "forwarding problem" has a good survey
here:
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2002/n1385.htm
The "perfect forwarding" solution (#7 in the above link) is working its
way through the committee now. Here is the proposed wording:
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2005/n1770.html
which is under review by the Core Working Group.
Anticipated syntax is:
template<typename T, typename T1, typename T2, typename T3>
void my_new(T1&& a1, T2&& a2, T3&& a3)
{
/* ... */
new T(std::forward<T1>(a1),
std::forward<T2>(a2),
std::forward<T3>(a3));
/* ... */
}
You will be able to call my_new with both cv-qualified lvalues and
rvalues (i.e. one overload fits all 3 parameter cases).
The "&&" is used for "rvalue reference" here instead of changing the
meaning of "&" (current or lvalue reference) in order to avoid backwards
compatibility problems and to preserve the current functionality of
unintended binding to rvalues.
A separate proposal:
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2004/n1704.pdf
is exploring the possibility of a language change that would allow a
single template function to simultaneously handle the 0 thru N parameter
case where N is arbitrarily large.
-Howard
---
[ comp.std.c++ is moderated. To submit articles, try just posting with ]
[ your news-reader. If that fails, use mailto:std-c++@ncar.ucar.edu ]
[ --- Please see the FAQ before posting. --- ]
[ FAQ: http://www.jamesd.demon.co.uk/csc/faq.html ]
|
|
| Back to top |
|
 |
|
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot vote in polls in this forum
|
|