【问题标题】:How does C++ know how to cast to a certain type?C++ 如何知道如何转换为某种类型?
【发布时间】:2020-09-07 20:26:12
【问题描述】:

如果我写

long long int module = (long long int)GetModuleHandle(L"test.dll");

C++ 如何知道如何转换 HMODULE?好像我是正确的 HMODULE 应该是一个结构。

我了解这对于 int、float 等基本类型是如何工作的,但是 对于程序员生成的,肯定有翻译吧?

【问题讨论】:

  • 编译器只是按照你的要求去做,不关心后果。指向结构的指针转换为long long int?你是老板,你懂的!结果有效吗?不是编译器的问题,是你的问题。唯一执行的“转换”是如何通过类型解释位。
  • 当您打开更激进的警告(如 -Wall 或等效警告)时,这说明了什么?
  • 一个HMODULE 是一个void*
  • auto module = GetModuleHandle(L"test.dll"); -- 不需要强制转换。
  • @PaulMcKenzie 这不是同一个代码,因为现在moduleHMODULE。如果你只是想删除演员,你会写HMODULE module = GetModuleHandle(L"test.dll");,即auto实际上在这里解决不了任何问题......我并不是说一定不要使用它,但它似乎与问题无关是否有演员表。从这个意义上说,演员阵容从不“必要”。

标签: c++ windows 64-bit


【解决方案1】:

嗯,它真的不能,除非代码告诉它如何做,例如通过转换运算符或构造函数。

有一些用于原始数字事物的内置规则,例如 intfloat,或 void*int……尽管后一个示例只能由 reinterpret_cast 或 C- 完成风格像你一样。那是因为除非“你最了解”,否则转换并没有真正的逻辑意义,这是你向编译器承诺的。

确实,像大多数句柄类型一样,HMODULE is actually an alias for a pointer type(特别是void*),尽管HMODULEs 指向的东西通常属于某种类类型。所以你将void* 转换为long long int,这是语言规则知道如何做的事情(ref 1ref 2)。

【讨论】:

    【解决方案2】:

    在 C++ 中,您基本上可以通过滥用类型系统来强制按您喜欢的方式对待可访问内存中的任何区域。例如,看看这个乱码,我将const std::string 重新解释为一个const 指针,该指针指向一个从int 到包含vector<double>struct Foo 的函数。现在,如果我尝试对f 执行任何操作,它会严重崩溃,但即使使用-Wall,代码也会编译,我得到的唯一警告是未使用f

    #include <functional>
    #include <vector>
    
    struct Foo {
        std::vector<double> d{};
    };
    
    using func_type = const std::function<Foo(int)>*;
    
    int main() {
        func_type f = reinterpret_cast<func_type>("This is a test");
    }
    

    正如有人指出的那样,HMODULE 只是 void*,因此您可以将其转换为您想要的任何内容。您只是获取它的内存位置并将其存储在long long int 中。我不知道你为什么要这样做,因为它没有用。

    【讨论】:

    • 这不是严格准确的:你不只是将内存位塞入一个整数。转换具有逻辑但实现定义的语义:“指针可以显式转换为任何大到足以容纳其类型的所有值的整数类型。映射函数是实现定义的。[注意:它旨在对于那些知道底层机器的寻址结构的人来说不足为奇。-结束注]" (ref) 至关重要的是,无论选择什么映射must be reversible
    • 实际上编译器可能会按照您的描述进行操作。 :)
    猜你喜欢
    • 2020-11-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-04-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多