C ++ Primer(5th ed。):Is“16.3 Overloading and Templates”在其所有的“更专业的”例子? [英] C++ Primer (5th ed.) : Is "16.3 Overloading and Templates" wrong in all its "more specialized" examples?
问题描述
C ++ Primer(第5版)的第16.3节 - 重载和模板 - 在存在候选函数模板实例化的情况下教授函数匹配过程。
以下是本节中使用的函数模板的声明:
使用std :: string;
template< class T> string debug_rep(const T&); / * 1 * /
template< class T>字符串debug_rep(T *); / * 2 * /
//与问题无关的定义
h3>
string s(SO);
debug_rep(& s);
string s(SO);
debug_rep(& s);
那么说生成的实例化将是:
-
debug_rep(const string *&)
(T
绑定到string *
) -
debug_rep(string *)
Q1 #1是否正确?不应该实例化 debug_rep(string * const&)
?
第二个例子
const string * sp =& s;
debug_rep(sp); // string literal type is const char [10]
be:
-
debug_rep(const string *&)
$ c> T 绑定到const string *
) -
debug_rep string *)
因此,实例化的候选将提供完全匹配,专用模板( - >#2)
Q2.1 #1是否正确?不应该实例化 debug_rep(const string * const&)
?
em>
第三个例子
debug_rep(SO world!); // string literal type is const char [10]
be:
-
debug_rep(const T&)
c> T 绑定到char [10]
) -
debug_rep string *)
因此,实例化的候选将提供完全匹配,专用模板( - >#2)
Q3.1 是 T
在#1中正确?应该不是 const char [10]
而是?
T
的推导类型实际上是上面的那个,我们可以确定它不是一个完全匹配吗?
使用std :: string;解决方案
template< class T> string debug_rep(const T&); / * 1 * /
template< class T>字符串debug_rep(T *); / * 2 * /
p>
string s(SO);
debug_rep(& s);
& s
产生 string 只能匹配
T $>的
T const&
c $ c>是 string *
。对于(2)中的 T *
,匹配 T
绑定到 string
。所以,如果你的引用是正确的,这本书是错误的
debug_rep(const string *& ;)
是一个可能的实例化: / p>
T
= string *
debug_rep(string * const&)
但是哪个实例化将被调用?
作为一般规则,最简单的匹配是优越的,但我从来没有设法记住确切的规则,所以,我问Visual C ++(因为其 typeid(T).name()
默认生成可读类型名称):
#include< iostream>
#include< string>
#include< typeinfo>
using namespace std;
template<类T>
struct Type {};
template< class T> auto debug_rep(T const&)// 1
- > string
{return string()+1 - > T =+ typeid(Type< T& }
template< class T> auto debug_rep(T *)// 2
- > string
{return string()+2 - > T =+ typeid(Type< T& }
auto main() - > int
{
字符串s(SO);
cout<< debug_rep(& s)<< endl;
cout<< 类型'int const'显示为<< typeid(Type< int const>)。name()<< endl;
}
并说:
2 - > T = struct Type< class std :: basic_string< char,struct std :: char_traits< char>,class std :: allocator< char> > >
类型'int const'显示为struct Type< int const>
对于你的第二个和第三个例子:显然作者得到了一些关于 const
。
Section 16.3 of C++ Primer (5th edition) - Overloading and Templates -, teaches the function matching procedure in the presence of candidate function template(s) instantiations.
Here are the declaration for the function templates used in this section:
using std::string;
template <class T> string debug_rep(const T &); /* 1 */
template <class T> string debug_rep(T *); /* 2 */
// definitions not relevant for the questions
First example
string s("SO");
debug_rep(&s);
it is then said that the generated instantiations will thus be:
debug_rep(const string *&)
(withT
bound tostring *
)debug_rep(string *)
Q1 Is it correct for #1 ? Should not it instantiate debug_rep(string* const &)
instead?
Second example
const string *sp = &s;
debug_rep(sp); //string literal type is const char[10]
it is then said that the generated instantiations will thus be:
debug_rep(const string *&)
(withT
bound toconst string *
)debug_rep(const string *)
Thus, both instantiated candidate would provide an exact match, selection being made on the more specialized template (-> #2)
Q2.1 Is it correct for #1 ? Should not it instantiate debug_rep(const string* const &)
?
Q2.2 Assuming the instantiated function is the one just above, can we affirm it is not an exact match any more ?
Third example
debug_rep("SO world!"); //string literal type is const char[10]
it is then said that the generated instantiations will thus be:
debug_rep(const T &)
(withT
bound tochar[10]
)debug_rep(const string *)
Thus, both instantiated candidate would provide an exact match, selection being made on the more specialized template (-> #2)
Q3.1 Is the type deduced for T
correct in #1 ? Should not it be const char[10]
instead ?
Q3.2 Assuming the deduced type for T
is actually the one just above, can we affirm it is not an exact match any more ?
You're given these declarations:
using std::string;
template <class T> string debug_rep(const T &); /* 1 */
template <class T> string debug_rep(T *); /* 2 */
In the invocation
string s("SO");
debug_rep(&s);
the &s
produces a string*
, which can only match the T const&
of (1) when T
is string*
. For the T*
in (2), there is a match for T
bound to string
. So, provided your quoting is correct, the book is wrong about
debug_rep(const string *&)
being a possible instantiation: there is no such.
The instantiation resulting from T
= string*
would instead be
debug_rep( string* const& )
But which instantiation will be called?
As a general rule the simplest match is superior, but I never manage to remember the exact rules, so, I ask Visual C++ (because its typeid(T).name()
produces readable type names by default):
#include <iostream>
#include <string>
#include <typeinfo>
using namespace std;
template< class T >
struct Type {};
template <class T> auto debug_rep( T const& ) // 1
-> string
{ return string() + "1 --> T = " + typeid(Type<T>).name(); }
template <class T> auto debug_rep( T* ) // 2
-> string
{ return string() + "2 --> T = " + typeid(Type<T>).name(); }
auto main() -> int
{
string s( "SO" );
cout << debug_rep( &s ) << endl;
cout << "The type 'int const' is shown as " << typeid(Type<int const>).name() << endl;
}
And it says:
2 --> T = struct Type<class std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> > > The type 'int const' is shown as struct Type<int const >
And so on for your second and third examples: apparently the author got some mixup regarding const
.
这篇关于C ++ Primer(5th ed。):Is“16.3 Overloading and Templates”在其所有的“更专业的”例子?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!