简体   繁体   English

运行时的函数模板类型推导

[英]Function template type deduction at runtime

I am trying to understand why the following compiles/runs despite the template type being resolved at run time. 我试图理解为什么以下编译/运行尽管在运行时解析模板类型。 Is it because the if/else calls to f alone are enough to tell the compiler to create void f<double>(double) and void f<std::string>(std::string) ? 是因为单独调用fif/else足以告诉编译器创建void f<double>(double)void f<std::string>(std::string)

test.hpp test.hpp

#include <type_traits>
#include <string>
#include <iostream>

template <typename T>
void f(T x) {
    if(std::is_same<T, std::string>::value)
        std::cout << "String: " << x;
}

test.cpp TEST.CPP

#include <iostream>
#include "test.hpp"

int main(int, char** argv) {
    double x(std::stod(argv[1]));

    if(x < 42) f(x);
    else f(std::to_string(x));

    return 0;
}

$ (clan)g++ -std=c++14 test.cpp
$ ./a.exe 41

$ ./a.exe 43
String: 43.000000

There is no run time template deduction going on here. 这里没有运行时模板扣除。 When you have 当你有

if(x < 42) f(x);

The compiler knows, at compile time, that x is a double so it stamps out 编译器在编译时知道x是双精度因此它会被标记出来

void f<double>(double)

Then in 然后进去

else f(std::to_string(x));

The compiler knows the return type of std::to_string is a std::string so it stamps out a 编译器知道std::to_string的返回类型是std::string因此它标记了一个

void f<std::string>(std::string)

To use. 使用。 Both functions exist at the same time and only one gets called at run time depending on what input you give the program. 这两个函数同时存在,并且在运行时只调用一个函数,具体取决于您为程序提供的输入。

Lets look at this example code provided by chris in his comment . 让我们看看chris在他的评论中提供的这个示例代码 Using 运用

#include <type_traits>

template <typename T>
__attribute__((used)) int f(T x) {
    if(std::is_same<T, int>::value)
        return 1;
    else
        return 2;
}

int main(int argc, char** argv) {
    if(argc > 1) return f(1);
    else return f(1.0);
}

Compiling with -O3 -std=c++1z -Wall -Wextra -pedantic generates the assembly 使用-O3 -std=c++1z -Wall -Wextra -pedantic生成程序集

main:                                   # @main
        xor     eax, eax
        cmp     edi, 2
        setl    al
        inc     eax
        ret

int f<int>(int):                        # @int f<int>(int)
        mov     eax, 1
        ret

int f<double>(double):                  # @int f<double>(double)
        mov     eax, 2
        ret

As you can see both template functions exist in the assembly and it is just the if in main that decides which one to call at run time. 正如您所看到的那样,程序集中存在两个模板函数,它只是if in main中决定在运行时调用哪一个。

  1. Compiler reads main , sees two calls to f , once with a string argument and once with an int 编译器读取main ,看到对f两次调用,一次使用字符串参数,一次使用int

  2. Generates two f s. 生成两个f s。 Calls to both functions are embedded in main. 对两个函数的调用都嵌入在main中。

  3. Your if statement causes one or another call. 您的if语句会导致一个或另一个呼叫。 So there is no template resolution in runtime. 因此运行时没有模板解析。 Such thing does not exist. 这样的事情不存在。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM