* Recursive template inline functions (C++)
@ 2008-05-21 22:05 Ling Li
0 siblings, 0 replies; only message in thread
From: Ling Li @ 2008-05-21 22:05 UTC (permalink / raw)
To: gcc
[-- Attachment #1: Type: text/plain, Size: 3268 bytes --]
Somehow g++ 3.4.3 can compile all the attached C++ programs, but g++ 4.2.4
can only compile the first one. I probably abused the template inline
functions in a bad way, but anyway could someone help to explain what I did
wrong?
===== Case 1 =====
template <class T>
inline T f (T i) {
T j = i - 1;
return g(&j) + i;
}
template <class T>
inline T g (T* i) {
if (*i == 0) return 0;
return f(*i);
}
=====
Both g++ 3.4.3 and 4.2.4 know where to find g() while instantiate f().
===== Case 2 (change the name of g() to f()) =====
template <class T>
inline T f (T i) {
T j = i - 1;
return f(&j) + i;
}
template <class T>
inline T f (T* i) {
if (*i == 0) return 0;
return f(*i);
}
=====
g++ 4.2.4 doesn't seem to know about the 2nd template function of f(), and
keeps coerce int* into int:
fwd-template-inline2.cpp: In function T f(T) [with T = int]:
fwd-template-inline2.cpp:14: instantiated from here
fwd-template-inline2.cpp:4: error: invalid conversion from int* to int
fwd-template-inline2.cpp: In function T f(T) [with T = int*]:
fwd-template-inline2.cpp:4: instantiated from T f(T) [with T = int]
fwd-template-inline2.cpp:14: instantiated from here
fwd-template-inline2.cpp:4: error: invalid operands of types int** and int*
to binary operator+
fwd-template-inline2.cpp: In function T f(T) [with T = int**]:
fwd-template-inline2.cpp:4: instantiated from T f(T) [with T = int*]
fwd-template-inline2.cpp:4: instantiated from T f(T) [with T = int]
fwd-template-inline2.cpp:14: instantiated from here
fwd-template-inline2.cpp:4: error: invalid operands of types int*** and
int** to binary operator+
fwd-template-inline2.cpp: In function T f(T) [with T = int***]:
fwd-template-inline2.cpp:4: instantiated from T f(T) [with T = int**]
fwd-template-inline2.cpp:4: instantiated from T f(T) [with T = int*]
fwd-template-inline2.cpp:4: instantiated from T f(T) [with T = int]
fwd-template-inline2.cpp:14: instantiated from here
...
===== Case 3 ====
#include <vector>
template <class T>
inline size_t f (const T* x) {
if (x) return f(*x);
return 0;
}
template <class T>
inline size_t f (const std::vector<T>& x) {
return x.size();
}
=====
Similar to case 2, g++ 4.2.4 doesn't see the 2nd definition, and complains
about no matching function.
fwd-template-inline3.cpp: In function size_t f(const T*) [with T =
std::vector<double, std::allocator<double> >]:
fwd-template-inline3.cpp:16: instantiated from here
fwd-template-inline3.cpp:5: error: no matching function for call to f(const
std::vector<double, std::allocator<double> >&)
I understand that adding a forward declaration of the 2nd definition, like
the line below, would solve the problem of Case 3 (and Case 2 as well).
template <class T>
inline size_t f (const std::vector<T>&);
However, I am not sure if the compiler would still honor the "inline" hint.
Actually, I don't even know if including "inline" in the forward
declaration make any sense, since forward declaration means the definition
is not available at this moment.
And anyway, g++ 3.4.3 is quite happy with all cases, so it is confusing
which g++ version actually does the correct thing.
Any opinions would be highly appreciated! Thanks!
--Ling
[-- Attachment #2: fwd-template-inline1.cpp --]
[-- Type: text/plain, Size: 200 bytes --]
template <class T>
inline T f (T i) {
T j = i - 1;
return g(&j) + i;
}
template <class T>
inline T g (T* i) {
if (*i == 0) return 0;
return f(*i);
}
int main () {
return f(3);
}
[-- Attachment #3: fwd-template-inline2.cpp --]
[-- Type: text/plain, Size: 200 bytes --]
template <class T>
inline T f (T i) {
T j = i - 1;
return f(&j) + i;
}
template <class T>
inline T f (T* i) {
if (*i == 0) return 0;
return f(*i);
}
int main () {
return f(3);
}
[-- Attachment #4: fwd-template-inline3.cpp --]
[-- Type: text/plain, Size: 265 bytes --]
#include <vector>
template <class T>
inline size_t f (const T* x) {
if (x) return f(*x);
return 0;
}
template <class T>
inline size_t f (const std::vector<T>& x) {
return x.size();
}
int main () {
std::vector<double> vd(10);
return f(&vd);
}
^ permalink raw reply [flat|nested] only message in thread
only message in thread, other threads:[~2008-05-21 22:05 UTC | newest]
Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2008-05-21 22:05 Recursive template inline functions (C++) Ling Li
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).