繁体   English   中英

为什么此函数将'const char *'强制转换为'void * const'而不是'const void *'

[英]Why does this function cast 'const char*' to 'void* const' and not 'const void*'

这是一个非常愚蠢的示例,我在Windows中使用线程将const_caststatic_cast包装到一个线程中时static_cast

// Somewhere in the OS API
using function_t = void(*)(void *);
void create_thread(function_t function, void *params);

template <typename T, typename U>
T static_const_cast(U ptr) {
  return const_cast<T>(static_cast<const T>(ptr));
}

void thread_proc(const void* name) {
  // ...
}

void test() {
  const char *name = "name";
  void *params = static_const_cast<void *>(name); // Fails
  // void *params = const_cast<void *>(static_cast<const void *>(name));
  // Succeeds (what I want to achieve with static_const_cast)
  create_thread(reinterpret_cast<function_t>(thread_proc), params);
}

但它无法在Visual Studio 2017上编译,因此我在Godbolt上尝试了gcc和clang,认为它肯定可以编译,但仍然拒绝错误消息(来自gcc 8.2):

error: invalid static_cast from type 'const char*' to type 'void* const'
                                                           ^^^^^^^^^^^^^

为什么它会尝试强制转换为void* const而不是预期的const void* 有什么明显的我想念的东西吗?

为什么此函数将'const char *'强制转换为'void * const'而不是'const void *'

因为您使用void *作为模板参数,并且在将const应用于模板参数时,它将变为void * const void *是一个指针(指向非const对象),将指针设为const会导致const指针,而不是指向const对象的(非const)指针。

您可以执行以下操作来实现所需的功能:

return const_cast<T>(
    static_cast<std::remove_pointer_t<T> const*>(ptr)
);

但是,我建议改用自定义类包装发送到线程的数据。 另外,请勿强制转换函数类型。 使用带有void*参数的函数,并将参数转换为函数。

struct params_t {
    const char *name;
};

static params_t params {"name"};

create_thread(thread_proc, &params);

不需要任何强制转换(显然在回调中除外)。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM