Friday, January 3, 2014

Why does this template code compile?

Newsgroup: comp.lang.c++

Subject: Why does this template code compile?

From: Peter <pilarp@...>

Date: Fri, 3 Jan 2014 16:25:54 -0800 (PST)



In "C++ Templates The Complete Guide" book by Vandevoorde

and Josuttis I found the following template definition

near the end of chapter 8.2 ("Template Arguments"):



template<template<typename T, T*> class Buf>

class Lexer

{

static char storage[5];

Buf<char, &Lexer<Buf>::storage> buf;

};



Buf is a template template argument whose template

arguments are: type parameter T and unnamed non-type

parameter - a pointer to T. In the definition of Lexer,

Buf is instantiated so that T = char and second argument

(of type T*) is &Lexer<Buf>::storage, but why is this

second substitution correct?

How does &Lexer<Buf>::storage resolve to char*?



Here's my reasoning.



Lex<Buf>::storage is of type char[5],

&Lex<Buf>::storage is of type char(*)[5].



If we had:



Buf<char, Lexer<Buf>::storage> buf;



instead of:



Buf<char, &Lexer<Buf>::storage> buf;



in the definition of Lexer template then

Lexer<Buf>::storage would decay to char*, but why

can the template be instantiated with

&Lexer<Buf>::storage as well? I tested both definitions

here:



http://www.compileonline.com/compile_cpp11_online.php



and they both compile.



However, if I try to instantiate Lexer with

&Lexer<Buf>::storage as second argument to Buf, I get

a compilation error as expected. Here's a complete example:





template<template<typename T, T*> class Buf>

class Lexer

{

static char storage[5];

Buf<char, &Lexer<Buf>::storage> buf;

};



template<typename T, T*>

class Foo

{

};



int main()

{

Lexer<Foo> lex;

return 0;

}



Now:



1) if I try to compile the above I get the following error:



main.cpp: In instantiation of 'class Lexer<Foo>':

main.cpp:15:15: required from here

main.cpp:5:37: error: could not convert template argument

'& Lexer<Foo>::storage' to 'char*'



2) if I change "&Lexer<Buf>::storage" to

"Lexer<Buf>::storage" the code compiles



3) if I comment out the instantiation of Lexer from main()

the code compiles with either &Lexer<Buf>::storage or

Lexer<Buf>::storage as second argument to Buf.



Can you explain what happens here and why Buf template can

be instantiated with either of the two arguments?







via Usenet Forums - Usenet Search,Free Usenet - comp.lang.c++ http://www.pocketbinaries.com/usenet-forums/showthread.php?164028-Why-does-this-template-code-compile&goto=newpost

View all the progranning help forums at:

http://www.pocketbinaries.com/usenet-forums/forumdisplay.php?128-Coding-forums

No comments:

Post a Comment