看板 C_and_CPP 關於我們 聯絡資訊
如題,C++ 有可能在未來支援 dependent types 嗎?如果支援的話大家覺得會長怎樣? 一些 cardinality 無限大的 types 不支援完全可以理解 但是像 integrals, std::array of integral 之類的 types 要支援應該不是問題? 到了 C++20,已經很多東西都有 constexpr 的版本了 用起來已經比之前的版本開心很多,但仍然和真正的 dependent types 有一段不小的差 距 如果有一天真的能把變數當作 template arguments 傳進 templates 裡,C++ 真的會有 用很多 或者退而求其次,至少支援個 constexpr function parameters 也好 這樣至少在 constexpr 的前提下有 dependent types 可以用 有 C++ 有沒有可能在未來支援 dependent types 的掛嗎? 或是有沒有看過相關的提案或是正式的討論呢? -- ※ 發信站: 批踢踢實業坊(ptt.cc), 來自: 174.112.13.222 (加拿大) ※ 文章網址: https://www.ptt.cc/bbs/C_and_CPP/M.1646301843.A.E7A.html
simon860730: integer...?03/04 09:04
CoNsTaR: 我的意思是 std::is_integral<T>::value 是 true 的那些03/04 11:35
CoNsTaR: types03/04 11:35
Lipraxde: 始終不明白 dependent types 的好處03/04 12:31
如果要說能讓 C++ 使用者比較有感的例子的話 dependent types 可以幫你省下一堆 switch case 或 if else 例如: switch(v) { case A: f<A>()... case B: f<B>()... ... case Z: f<Z>()... } 有了 dp types 就可以變成一行: f<v>()...
sarafciel: C++要弄non-constexpr dependent type應該很難XD03/04 13:53
sarafciel: constexpr dependent types的話 我覺得現在已經是了03/04 13:55
sarafciel: 只是寫起來很費工而已03/04 13:55
如果把所有 cardinality 小於某個大小的 types 的所有可能都先在 compile-time 算好 ,這樣會有什麼問題嗎? 或是如果用 [[exhaustive]] 之類的 attributes 來幫指定的 type 或 function 打開 d p types 支援,沒標的就維持跟以前一樣呢? 現在 function parameters 還是不能傳進 templates 裡面,我覺得不行 QQ
Lipraxde: Compile 時都先算好,打算付出多少成本獲得多少收穫?03/05 11:10
Lipraxde: 不同 type codegen 出來的東西是不一樣的耶,雖然有印03/05 11:13
如果預設 cardinality 256 以下才自動開 dp types(這個數字應該可以用編譯器參數調 整),然後可以用 attribute 說不論某個 type 多大(只要非無限大),我想要他無視 那個 cardinality 上限支援 dp types 這樣呢?
Lipraxde: 象看過用 JIT 來做 (用於加速數學計算),但忘記關鍵字03/05 11:13
Lipraxde: 了QQ03/05 11:13
嗯,JIT 建表加速聽起來很合理 XD
LPH66: 就算寫 f<v>(), 實際照 v 的值去選要呼叫的 f<A> 還是得在03/05 11:32
LPH66: runtime 做吧 (在 v 非 constexpr 的前提下)03/05 11:33
LPH66: 那這其實跟寫個大 switch 好像沒什麼差別03/05 11:34
先不提如果 v 是 std::size_t 而且所有 v 的可能性你都需要自己 map 的這種極端情況 ,有趣的是如果可以寫 x = f<v>() 的話,其實根本就可以不用擔心 v 實際上有哪些可 能性,例如你就可以寫: // concrete V<...> specializations can be ad-hoc defined by user template <std::size_t Z> struct V; // and this would still be valid [] (X x) { return f<V<g(x)>()>(); } 這樣你事先不需要知道 user 實際上會 specialize 哪些 V,只要 g 的邏輯讓每個 g(x) 都能確實對上一個 specialization,編譯就會過(雖然這樣好像比較像 refinement ty pes,less like 一般的 dependent types,但意思應該有傳達到,而且這種做法也滿符 合 C++ templates 有用到才檢查的傳統的?只是現在變成"runtime 有可能用到"才檢查 而已 XD)
LPH66: 如果硬要把它藏起來, 我能想到接近的是 std::visit03/05 11:35
LPH66: (C++17 新加的內建 Visitor Pattern)03/05 11:35
我覺得這好像只是把 switch case 換一種方式寫而已?f 和 v 的關係實際上還是 detac hed 的,i.e. 每當 v 又多了一種可能性就又要回來這邊補上 Edit: 改了一下標題,這個題目討論起來應該會更有趣 XD
LPH66: 對, 所以我說這是硬要藏起來而已 03/05 23:31
LPH66: 這樣看起來其實你的 v 用個 enum 表示好像比較像你在想的?03/05 23:35
以上面那個例子來說的話,主要想表達的是當一般程式想和 constexpr 的程式接起來的 時候非得有個手動生出來的 if else/switch case/std::visit/lookup table etc... 但如果能把像對 templates 那樣 "用到才檢查" 的規則擴展到對傳進 templates 的一般 變數 "runtime 有可能用到才在 compile-time 先算好" 的話,就好象實現了部分 depen dent types/refinement types 的功能了,實際感受到的改變就好象是 compiler 幫你自 動建了一個 switch case/lookup table 一樣,而且不需要自己手動維護
LPH66: 可能狀況數很少, 所以可以先產生起來放03/05 23:35
LPH66: 現在對於這種 use case 好像也就是手動生出來放之後03/05 23:37
LPH66: 收到一個對照表裡參照, 要用時照 v 值去對照表裡找出來用03/05 23:38
話說之前看過有人實測 switch case v.s. 查表的效能比較 結果查表贏了 switch case/if else 滿多的,這個結果可以代表什麼嗎?
Lipraxde: 恩...最終還是會需要在 runtime 時 dispatch 吧?如果03/06 00:12
如果是單一個 function 的時候看起來好像沒什麼差 但如果 f(g(x)) 的話,runtime 就可以不需要查表兩次 因為 compile-time 就把所有 g 的輸入 f 會有什麼輸出都算好了
Lipraxde: 說都要 compile time 做好的話... template metaprogra03/06 00:12
Lipraxde: mming 還不夠好玩嗎 Orz03/06 00:13
呃,主要就是因為想要讓一般函數、變數能夠和現成的 TMP 無縫接軌,否則目前的 TMP 說實話真的有點雞肋... 什麼 first class types 啦之類的都好說,至少先讓一般變數也能傳進 templates 裡吧 QQ ※ 編輯: CoNsTaR (174.112.13.222 加拿大), 03/06/2022 13:08:20
adks3489: 像P1045R1這個提案嗎? 03/06 21:22