2017-02-03 38 views
1

为什么模板函数在LLVM-IR中不显示,如果函数未被调用,当从C++代码发出LLVM IR时, 不像其他类型的函数(int,float ...)会出现在llvm中IR 例如:下面的函数func1犯规秀LLVM IR为什么模板函数不能显示在LLVM-IR中?

template <class tmp> 
tmp func1() { 
    // ... 
} 

但这个功能func2始终显示在LLVM IR

int func2() { 
    // ... 
} 
+1

这不是*模板函数*。这是一个*函数模板*。这不是一种功能,而是未来功能的蓝图。这是完全无关紧要的。'func '将是*模板函数*,即所有模板参数已知的*函数模板*。这*实例化模板,使其“实现”。 – AnT

回答

5

这是导致你的模板不是功能:它们是功能模板。在用参数实例化之前,它们不是调查结果。例如,拿这个代码:

template<typename T> 
T foo() { /* ... */ } 

那也不会输出任何代码。

但这在另一方面:

template<typename T> 
T foo() { /* ... */ } 

int test() { 
    return foo<int>(); 
} 

将输出两个testfoo<int>代码。

您也可以手动实例化这样的一个模板:

template int foo<int>(); 
4

这与how C++ templates work做。由于编译器在调用函数(或者更确切地说,当您实例化它)之前不知道tmp是什么,它不知道如何为它编写代码。例如,考虑这个模板:

template <typename T> 
T add(T left, T right) { 
    return left + right; 
} 

如果T是一个整数,那么函数体是一个整数加。如果T是双精度浮点数,则它是一个浮点数。如果Tstd::string,这是一个函数调用std::string::operator+。由于在任何C++程序中都有很多类型,并且可以添加其中的很多类型,并且几乎每种类型都以不同的方式添加,所以在知道此类型之前,不能为该函数创建代码。如果它试图对所有可能的类型执行此操作,那么您可能会遇到可能实现的组合式爆炸,几乎所有这些操作都不会被使用。你的编译时间和二进制文件的大小将会很大,如果有什么好处的话,很少。


事情变得稍微复杂一点,class templates。类模板的实例化实际上并不需要实例化所有函数,如果它们没有被调用。回到我们的例子,如果我们不是这样写道:

template <typename T> 
class Adder { 
    T add(T left, T right) { 
     return left + right; 
    } 
}; 

Adder<int> a; 

仍然不会实例Adder<int>::add即使编译器拥有所有的信息,知道add<int>是潜在的有趣,因为你不实际调用或以其他方式实例化它。

相关问题