【问题标题】:Why does this pointer_cast fail?为什么这个 pointer_cast 会失败?
【发布时间】:2021-10-23 16:45:03
【问题描述】:

这个if 测试工作正常(已经做了多年):

if (m_pMapSPtrEvents->Lookup(strKey, (void*&)psEvent))
{
    if (psEvent != nullptr)
    {
        bActivate = TRUE;
        strTipText = psEvent->strEvent;
    }
}

但是如果我把它改成:

if (m_pMapSPtrEvents->Lookup(strKey, pointer_cast<void*&>(psEvent)))
{
    if (psEvent != nullptr)
    {
        bActivate = TRUE;
        strTipText = psEvent->strEvent;
    }
}

`pointer_cast 在哪里:

template<typename T, typename U> static T inline pointer_cast(U src) noexcept
{
    static_assert(sizeof(T) >= sizeof(U), "Invalid pointer cast"); // Check sizes!
    __pragma(warning(suppress:26490)) // Note: no semicolon after this expression!
        return reinterpret_cast<T>(src);
}

失败了。投射结构指针 (SPECIAL_EVENT_S *psEvent) 的现代方式是什么?

m_pMapSPtrEvents 的类型为 CMapStringToPtr


我应该指出:

  • 我在 IDE 中没有收到任何视觉警告。
  • 编译没有错误。
  • 我运行它时它不会断言。
  • 但它不会检测到 if 子句,因此不会显示工具提示。

...除非我恢复到 c 风格的演员表。


更新

如果我按照建议删除&amp;,则会出现构建错误:

4>MyMonthCalCtrl.cpp
4>D:\My Programs\2022\MeetSchedAssist\Meeting Schedule Assistant\MyMonthCalCtrl.cpp(72,8): error C2664: 'BOOL CMapStringToPtr::Lookup(LPCTSTR,void *&) const': cannot convert argument 2 from 'T' to 'void *&'
4>        with
4>        [
4>            T=void *
4>        ]
4>C:\Program Files\Microsoft Visual Studio\2022\Preview\VC\Tools\MSVC\14.30.30704\atlmfc\include\afxcoll.h(1264,7): message : see declaration of 'CMapStringToPtr::Lookup'
4>Done building project "Meeting Schedule Assistant.vcxproj" -- FAILED.

【问题讨论】:

  • 如果您删除演员表中的参考规范(&amp;)会发生什么?无论如何,我猜Lookup 函数调用会作为参考。
  • 我知道。但我认为引用类型在某种程度上令人困惑。如果按照我链接的答案中的建议,存在某种未检测到的 void* 类型的取消引用,那么这将在各种工作中抛出各种扳手。也许我需要修改pointer_cast 的代码...
  • 该函数在return reinterpret_cast&lt;T&gt;(src) 下看起来确实很奇怪,我收到警告“局部变量或临时的返回地址:src”。尝试使用m_pMapSPtrEvents-&gt;Lookup(strKey, reinterpret_cast&lt;void*&amp;&gt;(psEvent))
  • 是的 - 需要重新考虑 pointer_cast 来处理引用类型转换。我会看看我是否能想出至少一个quick-fix 来警告/失败这些类型,虽然......
  • 作为权宜之计,您可以将其添加为pointer_cast 函数的第一行:static_assert(!std::is_reference&lt;T&gt;::value, "Cannot pointer_cast to a reference!");(您还需要#include &lt;type_traits&gt;)。

标签: visual-c++ casting mfc


【解决方案1】:

我相信有人会整理出一个描述为什么 pointer_cast 失败的答案——他们会比我更能解释。


解决方法

我的回答提供了解决方法。鉴于这些警告的上下文(MFC 应用程序)以及存在必须使用reinterpret_cast 的有效实例,我在stdafx.h 文件中添加了以下行:

#pragma warning( disable : 26490)

并使用查找/替换将所有pointer_cast 还原为reinterpret_cast。应用程序现在运行正常。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-07-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-09-29
    • 2021-03-17
    • 1970-01-01
    相关资源
    最近更新 更多