在成员函数中使用此和属性返回类型? [英] Using this and attributes in member function trailing return types?

查看:731
本文介绍了在成员函数中使用此和属性返回类型?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在此 answer 我给了,使用这个和类的属性 _arg 在尾部返回类型中作为 decltype 表达式的一部分。



既不是clang 3.0(见下文)也不是 gcc 4.5.2 接受了。

  #include< iostream> 

class MyClass {
public:
MyClass(int i):_arg(i){}

template< typename F>
自动应用(F& f) - > decltype(f(_arg)){
return f(_arg);
}

template< typename F>
自动应用(F& f) - > decltype(f(* this,_arg)){
return f(* this,_arg);
}

private:
int _arg;
};

struct Id {
template< typename V>
V operator()(V v)const {return v; }
};

struct ComplexId {
template< typename C,typename V>
V operator()(C const& V; v){return v + 1; }
};

int main(){
Id id; ComplexId complex;

MyClass c(0);

std :: cout<< c.apply(id)<< < c.apply(complex)<< \\\
;
}

clang 3.0说:

  $ clang ++ -std = c ++ 11 -Weverything test.cpp 
test.cpp:8:38:error:using undeclared identifier'_arg'
自动应用(F& f) - > decltype(f(_arg)){
^
test.cpp:8:45:error:type name需要一个说明符或限定符
auto apply(F& f) decltype(f(_arg)){
^
test.cpp:8:45:error:C ++需要一个所有声明的类型说明符
auto apply(F& f) decltype(f(_arg)){
~~~~~~~~~ ^
test.cpp:8:7:错误:'auto'返回没有结尾返回类型
自动应用F& f) - >在非静态成员函数之外使用'this'
auto apply(F& f) - > decltype(f(* this,_arg)){
^
test.cpp:13:52:error:type name需要一个说明符或限定符
auto apply(F& f) - > ; decline(f(* this,_arg)){
^
test.cpp:13:52:error:C ++需要一个所有声明的类型说明符
auto apply(F& f) > decltype(f(* this,_arg)){
~~~~~~~~~~
test.cpp:13:7:错误:'auto'返回没有结尾返回类型
自动应用(F& f) - > decltype(f(* this,_arg)){
^
生成8个错误。

哼...不太好。



但是,C ++ 11的支持在大多数编译器中是最好的,我找不到标准(n3290)中提到的具体限制。



评论,Xeo建议它可能是标准的缺陷...



这是允许与否? >

奖金:并执行更多最新版本的clang / gcc支援此功能?

方案

我误解了。这是某点的缺陷,但最终已解决并投票进入FDIS



§5.1.1[expr.prim.general]


如果声明声明了一个类 X 的成员函数或成员函数模板,则表达式 this 可选的 cv-qualifer-seq 和结束之间的 cv-qualifer-seq X



$ b $ b

因此,Clang和GCC只是没有正确实现它。

  struct X {
//'this'存在于|标记
void f()const volatile | {
} |
auto g()const volatile | - > void {
} |
};


In this answer I gave, it made sense to use this and the attribute of the class _arg in the trailing return type as part of the decltype expression. It's possible to do without, but inconvenient.

Neither clang 3.0 (see below) nor gcc 4.5.2 accepted it though.

#include <iostream>

class MyClass {
public:
  MyClass(int i): _arg(i) {}

  template <typename F>
  auto apply(F& f) -> decltype(f(_arg)) {
    return f(_arg);
  }

  template <typename F>
  auto apply(F& f) -> decltype(f(*this, _arg)) {
    return f(*this, _arg);
  }

private:
  int _arg;
};

struct Id {
  template <typename V>
  V operator()(V v) const { return v; }
};

struct ComplexId {
  template <typename C, typename V>
  V operator()(C const&, V v) { return v + 1; }
};

int main() {
  Id id; ComplexId complex;

  MyClass c(0);

  std::cout << c.apply(id) << " " << c.apply(complex) << "\n";
}

clang 3.0 says:

$ clang++ -std=c++11 -Weverything test.cpp
test.cpp:8:38: error: use of undeclared identifier '_arg'
      auto apply(F& f) -> decltype(f(_arg)) {
                                     ^
test.cpp:8:45: error: type name requires a specifier or qualifier
      auto apply(F& f) -> decltype(f(_arg)) {
                                            ^
test.cpp:8:45: error: C++ requires a type specifier for all declarations
      auto apply(F& f) -> decltype(f(_arg)) {
                          ~~~~~~~~          ^
test.cpp:8:7: error: 'auto' return without trailing return type
      auto apply(F& f) -> decltype(f(_arg)) {
      ^
test.cpp:13:39: error: invalid use of 'this' outside of a nonstatic member function
      auto apply(F& f) -> decltype(f(*this, _arg)) {
                                      ^
test.cpp:13:52: error: type name requires a specifier or qualifier
      auto apply(F& f) -> decltype(f(*this, _arg)) {
                                                   ^
test.cpp:13:52: error: C++ requires a type specifier for all declarations
      auto apply(F& f) -> decltype(f(*this, _arg)) {
                          ~~~~~~~~                 ^
test.cpp:13:7: error: 'auto' return without trailing return type
      auto apply(F& f) -> decltype(f(*this, _arg)) {
      ^
8 errors generated.

Hum... not so great.

However, the support of C++11 is hacky at best in most compilers and I could not find specific restrictions mentionned in the Standard (n3290).

In the comments, Xeo suggested that it might have been a defect in the Standard...

So, is this allowed or not ?

Bonus: and do more recent versions of clang / gcc support this ?

解决方案

I misremembered. It was a defect at some point, but was eventually resolved and voted into the FDIS.

§5.1.1 [expr.prim.general]

If a declaration declares a member function or member function template of a class X, the expression this is a prvalue of type "pointer to cv-qualifier-seq X" between the optional cv-qualifer-seq and the end of the function-definition, member-declarator, or declarator.

As such, Clang and GCC just don't implement it correctly yet.

struct X{
  // 'this' exists between the | markers
  void f() const volatile | {
  } |
  auto g() const volatile | -> void {
  } |
};

这篇关于在成员函数中使用此和属性返回类型?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆