写了一个编译期执行的fibonacci模板:
[code]
template fibonacci(long n){
static if(n <= 2)
const long fibonacci = 1;
else
const long fibonacci = fibonacci!(n-1) + fibonacci!(n-2);
}
static long a = fibonacci!(40);
[/code]
D语言新支持的编译期执行函数也可以完成:
[code]
long fibonacci(long n){
if (n <= 2) return 1;
return fibonacci(n-1) + fibonacci(n-2);
}
static long a = fibonacci(40);
[/code]
这2种实现,我原想编译效率应该都比较低,因为编译期执行是要花编译时间的。结果前一种编译效率非常高,后一种则比较低。仔细想想,的确应该是这样,这与模板产生代码的机制有关。
模板在实例化时,会根据参数产生出不同的代码。比如上面的第一个例子,fibonacci!(1)和fibonacci!(2)就会实例化出2份代码,所以fibonacci!(40)相当于产生了这样一组代码:
[code]
// ....
const long fibonacci_38 = fibonacci_37 + fibonacci_36;
const long fibonacci_39 = fibonacci_38 + fibonacci_37;
const long fibonacci_40 = fibonacci_39 + fibonacci_38;
static long a = fibonacci_40;
[/code]
把每一个值都给缓存下来了,效率当然高了,我们使用相同的缓存策略也可以缩短函数的运行时间。
编译期执行的函数则没有这个优点,它和普通的函数没有区别,不同点在于它在编译的时候运行。把编译器看成一种动态语言运行环境,那么编译“编译期执行的函数”的过程就像是运行动态语言程序的过程。如果程序中存在大量编译期执行函数,可能极大地降低编译效率,对于它的使用应该尽量避免。
模板提供的是一种声明式语法,在复杂的静态执行逻辑面前有时候会显得力不从心,编译期执行函数在解决这个问题的同时,却带来了上面这种副作用。如果能把两者的优点结合起来,用函数的语法来写程序,由编译器生成优化的模板代码,这种编译期执行才可以大量使用。
[code]
template fibonacci(long n){
static if(n <= 2)
const long fibonacci = 1;
else
const long fibonacci = fibonacci!(n-1) + fibonacci!(n-2);
}
static long a = fibonacci!(40);
[/code]
D语言新支持的编译期执行函数也可以完成:
[code]
long fibonacci(long n){
if (n <= 2) return 1;
return fibonacci(n-1) + fibonacci(n-2);
}
static long a = fibonacci(40);
[/code]
这2种实现,我原想编译效率应该都比较低,因为编译期执行是要花编译时间的。结果前一种编译效率非常高,后一种则比较低。仔细想想,的确应该是这样,这与模板产生代码的机制有关。
模板在实例化时,会根据参数产生出不同的代码。比如上面的第一个例子,fibonacci!(1)和fibonacci!(2)就会实例化出2份代码,所以fibonacci!(40)相当于产生了这样一组代码:
[code]
// ....
const long fibonacci_38 = fibonacci_37 + fibonacci_36;
const long fibonacci_39 = fibonacci_38 + fibonacci_37;
const long fibonacci_40 = fibonacci_39 + fibonacci_38;
static long a = fibonacci_40;
[/code]
把每一个值都给缓存下来了,效率当然高了,我们使用相同的缓存策略也可以缩短函数的运行时间。
编译期执行的函数则没有这个优点,它和普通的函数没有区别,不同点在于它在编译的时候运行。把编译器看成一种动态语言运行环境,那么编译“编译期执行的函数”的过程就像是运行动态语言程序的过程。如果程序中存在大量编译期执行函数,可能极大地降低编译效率,对于它的使用应该尽量避免。
模板提供的是一种声明式语法,在复杂的静态执行逻辑面前有时候会显得力不从心,编译期执行函数在解决这个问题的同时,却带来了上面这种副作用。如果能把两者的优点结合起来,用函数的语法来写程序,由编译器生成优化的模板代码,这种编译期执行才可以大量使用。