为什么我的模板功能无法内联

时间:2016-09-10 13:47:46

标签: c++ templates lambda inline

我编写了一个可以在其中存储lambda函数的类,以确保在函数退出之前释放所有资源。

我使用cat fileName | tee fileName MSVC2015Release模式下测试我的代码。

但是,我发现/O2无法内联,并且会生成一个小函数。

GenerateScopeGuard

看起来与异常处理相关。实际上,如果我禁用C ++异常,则函数内联,但不适用于int main() { 01031C00 55 push ebp 01031C01 8B EC mov ebp,esp 01031C03 51 push ecx auto func = GenerateScopeGuard([] {printf("hello\n"); }); 01031C04 8D 4D FC lea ecx,[func] 01031C07 E8 24 00 00 00 call GenerateScopeGuard<<lambda_8b2f3596146f3fc3f8311b4d76487aed> > (01031C30h) return 0; 01031C0C 80 7D FD 00 cmp byte ptr [ebp-3],0 01031C10 75 0D jne main+1Fh (01031C1Fh) 01031C12 68 78 61 03 01 push offset string "hello\n" (01036178h) 01031C17 E8 24 00 00 00 call printf (01031C40h) 01031C1C 83 C4 04 add esp,4 01031C1F 33 C0 xor eax,eax } 01031C21 8B E5 mov esp,ebp 01031C23 5D pop ebp 01031C24 C3 ret return ScopeGuard<T>(std::forward<T>(func)); 01031C30 C6 41 01 00 mov byte ptr [ecx+1],0 01031C34 8B C1 mov eax,ecx } 01031C36 C3 ret 。为什么呢?

这是我的代码。

/EHsc

2 个答案:

答案 0 :(得分:1)

最近推出的非静态成员初始化功能似乎让MSVC编译器感到困惑。初始化的构造函数似乎解决了这个问题:

ScopeGuard()
    : dismissed_(false)
{
}

答案 1 :(得分:0)

使用-O3 -std = c ++ 14进行编译:

gcc 5.4的输出:

main:                                   # @main
        pushq   %rax
        movl    $.Lstr, %edi
        callq   puts
        xorl    %eax, %eax
        popq    %rcx
        retq

.Lstr:
        .asciz  "hello"

clang 3.8的输出:

__forceinline

这没有非标准{{1}}属性。

您确定已启用优化吗?

是否生成了此函数但未被main调用?