[問題] overload 加上 namespace 之後會 fail

作者: johnjohnlin (嗯?)   2014-07-31 15:23:09
呃我又來問問題了......
開發平台(Platform): (Ex: VC++, GCC, Linux, ...)
gcc version 4.8.2 (Ubuntu 4.8.2-19ubuntu1)
有用到 C++11,不過應該跟 C++11 沒關
問題(Question):
加上 namespace 之後 compiler 會到達編譯 template 深度上限
不過我想問的是為什麼不加的時候不會(見下面程式碼)
我有上網找過資料了,有一些類似的情形
可是好像又不太一樣
餵入的資料(Input):
N/A
預期的正確結果(Expected Output):
加不加 namespace 都一樣(見下面程式碼)
錯誤結果(Wrong Output):
如問題描述
使用 g++ -ftemplate-depth=15 -std=c++11 編譯可通過
加上 -DMAKE_FAIL (放入 namespace 的使用)之後就會炸掉
程式碼(Code):(請善用置底文網頁, 記得排版)
http://pastebin.com/nAwHMeCr
黃色是加上 namespace 的時候用
1 #include <type_traits>
2 #include <iostream>
3
如果用 namespace 包起來
就不能編譯
4 #ifdef MAKE_FAIL
5 namespace detail {
6 #endif
7
這個 template 編譯期遞迴呼叫自己
在沒有 namespace 的時候可以動
不過我覺得不加 namespace 的時候能編譯才是詭異的狀況
因為他可以用 template 自己本身實現下一層遞迴
所以進編譯期的無窮迴圈才是合理
8 template<
9 int CUR_IDX,
10 class PtrType,
11 class Func,
12 class LeftDistance
13 >
14 void _set_nth_element(
15 PtrType p,
16 Func f,
17 LeftDistance
18 )
19 {
20 _set_nth_element<CUR_IDX+1>(
p, f 直接傳下去
21 p, f,
把剩多遠傳下去,如果剩下 0 會 match 下面那個 template
22 std::integral_constant<int, LeftDistance::value-1>()
23 );
24 }
25
用 overload 宣告上面那個函數遞迴尾端的 case
integral_constant 0 的 時候就會 match
26 template<
27 int CUR_IDX,
28 class PtrType,
29 class Func
30 >
31 void _set_nth_element(
32 PtrType p,
33 Func f,
34 std::integral_constant<int, 0>
35 )
36 {
37 f(p+CUR_IDX);
38 }
39
40 #ifdef MAKE_FAIL
41 }
42 #endif
43
理論上等價於 f(p+N),N 為編譯期常數
透過呼叫 _set_element_nth 來達成
44 template<
45 int N,
46 class PtrType,
47 class Func
48 >
49 void set_nth_element(
50 PtrType p,
51 Func f
52 )
53 {
54 #ifdef MAKE_FAIL
55 using namespace detail;
56 #endif
57 _set_nth_element<0>(p, f, std::integral_constant<int, N>());
58 }
59
60 int main(int argc, char const* argv[])
61 {
62 int p[10] = {};
63
64 std::cout << p[7] << std::endl;
65 set_nth_element<7>(p, [] (int *p) -> void {
66 *p = 100;
67 });
68 std::cout << p[7] << std::endl;
69 return 0;
70 }
作者: carylorrk (carylorrk)   2014-07-31 15:31:00
看得痛苦 程式可以分開來貼在 ideone 嗎...未看先猜會不會加了 namespace 找不到特化的 baseline?
作者: johnjohnlin (嗯?)   2014-07-31 15:37:00
我有貼程式碼連結在上面為什麼會找不到特化,不是在同一個 namespace 下面?應該是問為什麼加了 namespace 之後能找到的就不一樣
作者: jackace (inevitable......)   2014-07-31 15:56:00
不加namespace: instantialize的時候在global中展開, 兩個

Links booklink

Contact Us: admin [ a t ] ucptt.com