8

这是一个返回数组引用的转换函数:

struct S { 
    typedef int int_array_20[20];
    operator int_array_20& ();
};

没有 可以做同样的事情typedef吗?我试过的:

struct S { 
    operator int (&()) [10];
};

但clang抱怨:

error: C++ requires a type specifier for all declarations
    operator int (&()) [10];
                  ~ ^
error: conversion function cannot have any parameters
    operator int (&()) [10];
    ^
error: must use a typedef to declare a conversion to 'int [10]'
error: conversion function cannot convert to an array type

做:

必须使用 typedef 来声明转换为 'int [10]'

意思typedef是不可缺少?

编辑
如果typedef有必要,不可能像下面这样创建转换函数模板,因为无法定义typedef模板,对吗?

struct S { 
    template<typename T, int N>
    operator T(&())[N];
};
4

1 回答 1

6

是的,这确实是必需的,我们可以通过 cppreference 部分用户定义的转换看到这一点,它说:

函数和数组运算符 [] 或 () 不允许在声明器中使用(因此转换为类型,例如指向数组的指针需要 typedef:见下文)。无论 typedef 是什么,conversion-type-id 都不能表示数组或函数类型。

我们可以在草稿 C++ 标准部分12.3.2 转换函数中找到它,它说:

转换类型 ID 不应代表函数类型或数组类型。转换函数 ID 中的转换类型 ID 是转换声明符的最长可能序列。[ 注意:这可以防止声明符运算符 * 与其对应的表达式之间的歧义。[ 例子:

&ac.operator int*i; // syntax error:
                    // parsed as: &(ac.operator int *)i
                    // not as: &(ac.operator int)*i

* 是指针声明符,而不是乘法运算符。—结束示例] —结束说明]

转换类型ID的语法如下:

conversion-type-id:
  type-specifier-seq conversion-declaratoropt
conversion-declarator:
  ptr-operator conversion-declaratoropt

这比语法看起来像这样的声明符更受限制:

declarator:
  ptr-declarator
  noptr-declarator parameters-and-qualifiers trailing-return-type
ptr-declarator:
  noptr-declarator
  ptr-operator ptr-declarator
noptr-declarator:
  declarator-id attribute-specifier-seqopt
  noptr-declarator parameters-and-qualifiers
  noptr-declarator [ constant-expressionopt] attribute-specifier-seqopt
  ( ptr-declarator )

克里斯提到的一种替代方法是使用身份类:

template <typename T>
struct identity
{
    typedef T type;
};

您可以按如下方式使用它:

operator typename identity<int(&)[10]>::type() ;
于 2014-07-19T02:22:00.257 回答