为什么const在``const t&'t t rvalue参考''中丢失了?

发布于 2025-01-20 08:27:45 字数 1189 浏览 1 评论 0原文

我正在开发一个模板类,并且给定传入类型 T 模板需要映射到“安全”常量引用。 (这本质上是为了避免在调用时将变异能力交给包装函数;请参阅 此处查看真实代码)。

原作者写了与此等效的内容:

template <typename T>
using SafeReference =
    std::conditional_t<std::is_scalar_v<T>, T, const T&>;

标量部分在这里并不有趣,但有趣的是const T&。这对我来说看起来是正确的,但事实并非如此:

struct Foo{};
using Bar = Foo&&;

// A failing static assert, and a reduced version. It turns out `const Bar&`
// is `Foo&`.
static_assert(std::is_same_v<const Foo&, SafeReference<Bar>>);
static_assert(std::is_same_v<const Foo&, const Bar&>);

我知道由于 参考折叠。我还了解到 const 可能“丢失”,因为它尝试将引用设为 const,而不是将引用的类型设为 const。但我什至不知道要谷歌什么才能确认这一点。

标准的哪一部分规定 const 在诸如 const T& 之类的表达式中“丢失”,模板化的 T 扩展为右值引用?

I'm working on a templated class, and given an incoming type T the template needs to map to a "safe" const reference. (This is essentially to avoid handing the ability to mutate to a wrapped function when it's called; see here for the real code).

The original author wrote something equivalent to this:

template <typename T>
using SafeReference =
    std::conditional_t<std::is_scalar_v<T>, T, const T&>;

The scalar part isn't interesting here, but what's interesting is const T&. This looks right to me, but it's not:

struct Foo{};
using Bar = Foo&&;

// A failing static assert, and a reduced version. It turns out `const Bar&`
// is `Foo&`.
static_assert(std::is_same_v<const Foo&, SafeReference<Bar>>);
static_assert(std::is_same_v<const Foo&, const Bar&>);

I understand that Foo&& becomes Foo& due to the rules for reference collapsing. I also understand that the const is probably "lost" because it tries to make a reference const rather than making the referred-to type const. But I don't even know what to Google in order to confirm that.

Which part of the standard says that the const is "lost" in an expression like const T& for a templated T expanding to an rvalue reference?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

热鲨 2025-01-27 08:27:45

标准的哪一部分说const在诸如const t&amp之类的表达中“丢失”了;对于模板t扩展到rvalue参考?

来自 dcl.ref/p6

如果A typedef-name ([[dcl.typedef],[temp.param])或A decltype-specifier ([dcl.type.decltype])表示一种是对T型引用的类型TR,尝试创建类型 lVALUE引用CV tr 创建类型 lvalue引用到<<代码> t ,尝试创建类型 rvalue引用CV TR 创建类型tr

这句话可能解释了您所看到的行为。

Which part of the standard says that the const is "lost" in an expression like const T& for a templated T expanding to an rvalue reference?

From dcl.ref/p6:

If a typedef-name ([dcl.typedef], [temp.param]) or a decltype-specifier ([dcl.type.decltype]) denotes a type TR that is a reference to a type T, an attempt to create the type lvalue reference to cv TR creates the type lvalue reference to T, while an attempt to create the type rvalue reference to cv TR creates the type TR.

The quote probably explains the behavior you're seeing.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文