首先先放链接:
这是很久之前做的很有意思的一个小项目,最近整理一下发出来。
先介绍Crisp是什么:Crisp是用C++模板实现的一门类lisp语言的编译期解释器。
放一段求阶乘的代码感受下:
Crisp的核心特性包括:lambda表达式、变量、递归函数、词法闭包、模式匹配、宏、代码即数据、call/cc( first class continuation )。
整体而言,Crisp的核心特性和scheme非常相似,其实本来是想按照R5RS的标准实现它的,但是嵌套模板和S表达式虽然相似,但毕竟还是两回事,硬搬过来很多东西都很别扭。索性就不管标准直接按照自己的喜好来了,于是我们就又多了一门lisp方言……
模板元编程是C++里重要的一部分,也是C++最晦涩难懂的部分之一。
c++模板是图灵完备的,这意味着什么?意味着理论上,你用python、java等任何一门通用语言能做的任何事情,用模板在c++编译期一样也能做了。当然受限于模板的限制,比如嵌套深度、输入输出等等,实际上模板并不能干那么多,但是使用模板来表达大部分纯逻辑计算,还是非常足够的。
事实上,模板可以看作是一门支持偏特化和递归的纯函数式语言。
模板的核心特性也就两个:
- 偏特化
- 递归
前者让模板具备分支选择的功能,后者让模板可以做迭代,于是模板就图灵完备了。
1.模板偏特化
template <bool value, typename Then, typename Else>
struct If {
using type = Then;
};
template <typename Then, typename Else>
struct If<false, Then, Else> {
using type = Else;
};
using t = If<true, int, bool>::type; // int
2.模板递归
template <int N>
struct sum {
static const int value = N + sum<N - 1>::value;
};
template <>
struct sum<1> {
static const int value = 1;
};
const int i = sum<3>::value; // 6
3.数据结构