C ++使用Struct

时间:2016-03-18 20:39:03

标签: c++ c++14

我知道std::tuple是从函数返回不同类型的多个变量的有效方法,如a talk by Herb Sutter中大约1:31:00所述(此代码示例是我的,不是来自视频)

auto get_tuple()
{
  return std::make_tuple(1, 2);
}

然后用

“解包”它
auto t = get_tuple();
int a = std::get<0>(t);
int b = std::get<1>(t);

int a;
int b;
std::tie(a, b) = get_tuple();

这些方法很棒,但我并不特别喜欢语法std::getstd::tie。我不会因为语法难以使用而使用有用的工具(在我个人看来),但是这样做呢?

auto get_struct()
{
  struct R
  {
    int a;
    int b;
  }

  return R{1, 2};
}

这为我编译(Visual Studio 2015),我更喜欢它的语法。我不想被指责过早优化,但我也会提到它似乎比元组快很多倍。大多数情况下,我只是喜欢语法。

那就是说,我知道这只是因为编译的东西并不意味着语言就是这样使用的。我不确定如何说出这个问题,但基本上,这是有效和定义的行为吗?我是否可以确信这将适用于其他主要编译器?坦率地说,即使在函数本身中定义了该类型,它也会推断它会推断出类型,所以我想确保它没问题。

这是我第一次在这个网站上发帖,如果我做错了,请提前抱歉。如果我这样做,请告诉我。

编辑:正如在回复中指出的那样,我声称本地结构比元组快几倍是完全错误的。我没有正确地进行测试。请参阅回复了解更多内容,我只是想编辑它以确保我不会误导任何人。

3 个答案:

答案 0 :(得分:4)

虽然本地结构符合标准,但我建议不要使用它(而不是元组)。首先,绩效指标可能不正确。

以下代码:

#include <tuple>

auto get_tuple()
{
  auto tup = std::make_tuple(1.0f, 2.0f);
  return tup;
}

auto get_struct() {
  struct R {
    float a, b;
  };

  return R{1, 2};
}

以优化模式生成以下ASM:

get_tuple():
        movq    %rdi, %rax
        movl    $0x40000000, (%rdi)
        movl    $0x3f800000, 4(%rdi)
        ret
get_struct():
        movq    .LC3(%rip), %xmm0
        ret
.LC3:
        .quad   4611686019492741120

因此只有两个movl指令更长。我不认为衡量这种效果是否可行。

而元组只是提供了比结构更多的东西!您可以根据元素(编译时)了解它的大小。您可以连接元组。您可以在它们上构建一个反射系统。您可以将它们与std::tie一起使用。您可以提供他们的类型。 (使用本地结构,它将自动一直向下)。当地的结构没有这样的东西。

答案 1 :(得分:3)

  

[...]这是有效且定义的行为吗?

是的,您可以声明一个本地类并返回它的实例。那很好。

  

我不想被指责过早优化,但我也会提到它似乎比元组快很多倍。

我怀疑运行时性能应该是由两个intstd::tuple<int, int>组成的本地结构之间的任何不同。编译时,确定tuple会慢一些。

因为一旦你返回一个本地类的实例,它不是真的本地,你可以把它变成一个非本地类:

struct R { ... };
R get_struct();

然后,关于这是否有效的问题甚至更少。

此外,您可以随时直接将元组输出插入解压缩的内容。查看Yakk's answer之类的内容:

std::tuple<int, int> get_tuple();

unpack(get_tuple(), [](int i, int j) { ... });
get_tuple() *then* [](int i, int j){ ... };

您可能也很高兴知道有一个structured bindings proposal可以直接允许:

auto {a, b} = get_tuple();

答案 2 :(得分:1)

这是有效的行为,你说它比使用元组更快是正确的。但是,您使用的是内置类型的简单案例。使用std::tuplestruct与用户定义类型的性能差异可能会使std::tuple更具吸引力,尽管语法不太优雅。