c++ Clang错误:调用一个私有构造函数,而实际上没有调用它们

hgtggwj0  于 2023-06-25  发布在  其他
关注(0)|答案(2)|浏览(122)

我做了一个类的静态函数,并将构造函数设为私有。现在我想使用函数。Clang说“构造函数是私有的”,而g则正常编译。
我不知道任何标准中是否有任何规则会以任何方式影响这一点。任何函数都可以生成一个变量,但它不能返回一个值。所以在上面的代码中,MyStruct::make不应该有任何错误,对吗?但Clang对此有不同的看法。
这是Clang应该做的吗?还是C中永远不应该做的事情?
我试图让C
更像Rust,这样我就不会对构造函数做一些意想不到的事情。我使用了g++,下面的代码可以工作。

#include <iostream>
#include <optional>
#include <utility>

class MyStruct {
public:
  static auto make(int val) -> MyStruct {
    MyStruct that(val);
    return that;
  };

  auto copy() -> MyStruct {
    MyStruct copy(this->val);
    return copy;
  }

  auto value() -> int { return this->val; }

private:
  MyStruct() = delete;

  MyStruct(int val) { this->val = val; }

  MyStruct(const MyStruct &other) { this->val = other.val; }

  int val;
};

auto main() -> int {
  auto my_struct = MyStruct::make(4);

  auto my_new_struct = my_struct.copy();

  std::cout << my_new_struct.value();
  std::cout << MyStruct::make(7).value();
}

然而,在Clang中,我遇到了一些错误:

main.cpp:30:20: error: calling a private constructor of class 'MyStruct'
  auto my_struct = MyStruct::make(4);
                   ^
main.cpp:24:3: note: declared private here
  MyStruct(const MyStruct &other) { this->val = other.val; }
  ^
main.cpp:32:24: error: calling a private constructor of class 'MyStruct'
  auto my_new_struct = my_struct.copy();
                       ^
main.cpp:24:3: note: declared private here
  MyStruct(const MyStruct &other) { this->val = other.val; }
  ^
2 errors generated.

换句话说,这是Clang应该做的,还是C++中永远不应该做的事情,为什么?

b4lqfgs4

b4lqfgs41#

例如,在这一行

auto my_struct = MyStruct::make(4);

如果不考虑复制/移动省略,则应该使用复制构造器。
在C++ 17标准之前,复制构造函数应该是可接受的,即使它的调用被省略了。
C++ 14标准(12.8复制和移动类对象)
1....[* 注 *:无论是否会发生复制省略,都必须执行此两阶段重载解决方案。它决定了在不执行省略时要调用的构造函数,并且即使调用被省略,所选的构造函数也必须是可访问的。- * 结束注解 * ]
要么将复制构造函数设为公共的,要么至少启用C++ 17标准的支持。

eqqqjvef

eqqqjvef2#

这取决于您的编译器版本和编译器标志。
对于Clang版本5.0.1,代码使用C++17(编译器开关-std=c++17)编译,但不在C++11(编译器开关-std=c++11)上编译。
See here that the code is compiling,设置了-std=c++17。但是如果我们设置-std=c++11

相关问题