在我的工作场所,我们倾向于使用 iostream,字符串,向量,地图和奇数算法或两个.我们实际上并没有发现很多情况,模板技术是问题的最佳解决方案.
我在这里寻找的是想法,以及可选的示例代码,它们展示了您如何使用模板技术为您在现实生活中遇到的问题创建新的解决方案.
作为贿赂,期待对你的答案进行投票.
模板的一般信息:
当您需要使用相同的代码但在不同的数据类型上运行时,模板非常有用,其中类型在编译时是已知的.当你有任何类型的容器对象时.
几乎所有类型的数据结构都是一种非常常见的用法.例如:单链表,双链表,树,尝试,哈希表,...
另一个非常常见的用法是排序算法.
使用模板的一个主要优点是可以删除代码重复.代码重复是编程时应该避免的最重要的事情之一.
您可以将函数Max实现为宏或模板,但模板实现将是类型安全的,因此更好.
而现在到了很酷的东西:
另请参阅模板元编程,这是一种在编译时而不是在运行时预先评估代码的方法.模板元编程只有不可变变量,因此其变量不能改变.由于这种模板,元编程可以看作是一种函数式编程.
查看来自维基百科的模板元编程示例.它显示了如何在编译时使用模板来执行代码.因此,在运行时,您有一个预先计算的常量.
templatestruct Factorial { enum { value = N * Factorial ::value }; }; template <> struct Factorial<0> { enum { value = 1 }; }; // Factorial<4>::value == 24 // Factorial<0>::value == 1 void foo() { int x = Factorial<4>::value; // == 24 int y = Factorial<0>::value; // == 1 }
我使用了很多模板代码,主要是在Boost和STL中,但我很少需要编写任何代码.
几年前的一个例外是在一个操作Windows PE格式EXE文件的程序中.该公司希望增加64位支持,但ExeFile
我编写的用于处理文件的类仅适用于32位的文件.操作64位版本所需的代码基本相同,但它需要使用不同的地址类型(64位而不是32位),这导致其他两个数据结构也不同.
基于对STL的使用一个模板来支持std::string
和std::wstring
,我决定尝试制作ExeFile
一个模板,用不同的数据结构和地址类型作为参数.有两个地方我仍然需要使用#ifdef WIN64
线条(处理要求略有不同),但这并不是很难.我们现在已经在该程序中获得了完整的32位和64位支持,并且使用该模板意味着我们所做的每一次修改都会自动应用于这两个版本.
我使用模板创建自己的代码的一个地方是实现策略类,如Andrei Alexandrescu在Modern C++ Design中所描述的.目前我正在开发一个项目,其中包括一组与BEA\h\h\h Oracle的Tuxedo TP监视器交互的类.
Tuxedo提供的一个工具是事务持久性队列,所以我有一个与队列交互的类TpQueue:
class TpQueue { public: void enqueue(...) void dequeue(...) ... }
但是,由于队列是事务性的,我需要决定我想要的事务行为; 这可以单独在TpQueue类之外完成,但我认为如果每个TpQueue实例在事务上都有自己的策略,那么它更明确且更不容易出错.所以我有一组TransactionPolicy类,例如:
class OwnTransaction { public: begin(...) // Suspend any open transaction and start a new one commit(..) // Commit my transaction and resume any suspended one abort(...) } class SharedTransaction { public: begin(...) // Join the currently active transaction or start a new one if there isn't one ... }
并且TpQueue类被重写为
templateclass TpQueue : public TXNPOLICY { ... }
所以在TpQueue中我可以根据需要调用begin(),abort(),commit(),但可以根据我声明实例的方式更改行为:
TpQueuequeue1 ; TpQueue queue2 ;