【问题标题】:How does the compiler deduce array size when defined as a template parameter?当定义为模板参数时,编译器如何推断数组大小?
【发布时间】:2016-06-21 19:03:37
【问题描述】:

我想知道,在以下代码中,编译器如何从 T (&arr)[arrsize] 函数参数推导出 arrsize 模板参数。例如,当我将一个 4 元素数组传递给它时,在我对函数的调用中没有提及数字 4,它正确地将 arrsize 参数确定为 4。但是,如果我正常传递数组(不是作为引用数组),也就是说,如果我将T (&arr)[arrsize] 更改为T arr[arrsize],它需要我在模板参数列表中显式提供arrsize 参数。

template <class T, int arrsize> void bubblesort(T (&arr)[arrsize], int order=1)
{
    if (order==0) return;
    bool ascending = (order>0);
    int i,j;
    for (i=arrsize; i>0; i--)
        for (j=0; j<i-1; j++)
            if (ascending?(arr[j]>arr[j+1]):(arr[j]<arr[j+1])) swap(arr[j],arr[j+1]);
}

所以我的问题是:

  1. 当我向函数传递对数组的引用时,编译器如何自动计算出arrsize 参数的值? (机制是什么?)

  2. 如果我正常传递数组,为什么编译器不能做同样的事情? (通常我的意思是不使用参考符号)

【问题讨论】:

  • Type arr[arrsize] 来自 C :-/

标签: c++ arrays templates reference template-argument-deduction


【解决方案1】:
  1. 它可以推断出大小,因为大小在编译时在调用上下文中是已知的。如果你有int a[4],并且你写bubblesort(a),那么编译器使用a的类型是int[4]的事实来推断arrsize为4。如果你尝试在@987654327时做bubblesort(p) @有int*类型,推演失败,编译出错。
  2. 如果你写T arr[arrsize]作为参数而不是T (&amp;arr)[arrsize],那么编译器会自动将声明重写为T* arr。由于arrsize不再出现在签名中,因此无法推断。

【讨论】:

  • 而2.是因为C.
  • 确切地说,因为旧的 C。我认为 C11 现在对 VLA 有类似的机制,但这与 C++11 无关。这两种语言在过去 20 年中出现了分歧。
【解决方案2】:

T arr[arrsize] 作为正式参数衰减为 T* arr,其中 arrsize 被完全忽略(实际上是该参数的数组性质)。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2011-06-27
    • 1970-01-01
    • 2020-01-21
    • 1970-01-01
    • 1970-01-01
    • 2020-04-23
    • 2015-03-13
    相关资源
    最近更新 更多