@溪流
1.
這是C++的缺陷…… 當初可能沒想到模板會被這么用,所以模板的功能其實還比較弱。
即使比較弱,也比java和C#強大,它是真正的代碼生成器……
C#的模板有一些約束,java的根本就是垃圾……
所以,模板還是很復雜的……
更本質(zhì)的說,其實體現(xiàn)的是一種ducking type,以單一函數(shù)作為組件之間交互的接口,而不是整個類型。ruby、python、lua這種動態(tài)類型語言都支持ducking type。而C++的模板只支持編譯時的ducking type。
C++社區(qū)給這種使用方式取了一個新的名字,叫concepts……
ducking type可能屬于新東西,而且很可能是意外產(chǎn)物(比如C++、python、lua;ruby好像是設(shè)計之初就考慮到這種用法),所以沒有提供專門的、顯示的通過短小的代碼(比如interface聲明)就可以表達的方式。只能通過文檔了……
說穿了,那些抵觸這種設(shè)計的,要么是偷懶不想看文檔,要么是已經(jīng)學會OO就不想學任何其他新事物,要么就是理解能力不夠……
心里疙瘩放下吧……
1.1. 雖然沒有專門的語法支持,但語言還是會檢查的,比如C++編譯時出錯,其他3個語言運行時出錯。
1.2. 比如python標準庫中,序列就沒有單獨的size()成員。所有的序列都通過len得到長度。已經(jīng)開始向這種思想靠攏了。
1.3. stl也這么多年了……
2
我對0依賴的看法不是"難",而是"通常沒有必要"。
應(yīng)該盡可能復用已有的優(yōu)秀的代碼。
盡可能向已有的,還過得去不算垃圾的標準靠攏,而不是自己獨立發(fā)明一套,結(jié)果在實際應(yīng)用中無法融合。
當然,這和練習編程技巧相抵觸……
所以我想提出一些建議,既可以練習;并且練習的結(jié)果是可以真正派上用場的。
比如,你可以考慮實現(xiàn)這樣一個函數(shù):
int vprintf_parse(void (*handler)(const char* s,void* context),void* context
const char* format, va_list arg );
按vprintf的標準去解析format與arg。每處理完一個%就調(diào)用handler一次。
由handler去考慮將s"輸出"到哪里。
這樣的話,vprintf_parse就可以用于很多很多地方:傳遞不同的hanlder給它就行。
當然,你也可以用它來實現(xiàn)string.format。 但一定要將vprintf_parse暴露出來,否則窩在string.format中太暴殄天物了。
更進一步…… 還可以提供一些讓客戶代碼擴展的機制,讓它自己定義%后的轉(zhuǎn)義符,以及處理方式。
3
我的意思是,這種方式是行不通的。
你要插入的元素是T吧?
std::set<std::list<T> > 元素是 std::list<T> 哦, 不是T了。
比較也是按std::less<std::list<T> >比較,而不是T。
不管multiset的底層實現(xiàn)是rbtree還是rbtree+list,都需要真正定義一個類,將底層實現(xiàn)的接口adapt一下才行。僅僅typedef是不夠的……
回復 更多評論