[英]Convert HWND to Hex String in C++
What is the best way to convert HWND
to Hex String in C++, I mean also with a "0x"
prefix? 在C ++中将HWND
转换为Hex String的最佳方法是什么,我的意思是"0x"
前缀?
HWND hWnd = FindWindow(L"Notepad", L"Untitled - Notepad");
MessageBox(nullptr, LPCWSTR(hWnd), L"Hello World!", MB_ICONINFORMATION | MB_OK | MB_DEFBUTTON1);
But I expect this to output 0x00000000
(assuming Notepad windows is not open) , but it always returns an empty string. 但我希望这输出0x00000000
(假设记事本窗口未打开),但它总是返回一个空字符串。
I also tried this answer , but I ended up with returning 0000000000000000
. 我也尝试了这个答案 ,但我最终还是返回0000000000000000
。
Anyone can help me on that conversion? 有人可以帮我转换吗?
To get a string representation of a hexadecimal number insert the 0x
literal followed by a handle into a stringstream: 要获取十六进制数字的字符串表示形式,请将0x
文字后跟句柄插入字符串流:
#include <Windows.h>
#include <sstream>
#include <iostream>
int main(){
HWND hWnd = FindWindow(L"Notepad", L"Untitled - Notepad");
std::stringstream ss;
ss << "0x" << hWnd;
std::cout << ss.str();
}
If you need to print out the result in a MessageBox use wide stringstream: 如果需要在MessageBox中打印出结果,请使用宽字符串流:
#include <Windows.h>
#include <sstream>
int main(){
HWND hWnd = FindWindow(L"Notepad", L"Untitled - Notepad");
std::wstringstream wss;
wss << "0x" << hWnd;
MessageBox(NULL, wss.str().c_str(), L"Hello World!", MB_ICONINFORMATION | MB_OK | MB_DEFBUTTON1);
}
What you are doing is not conversion. 你在做什么不是转换。 You just cast hWnd
to a pointer to string. 你只需将hWnd
转换为指向字符串的指针。 Almost always it will not point to a valid string, producing an undefined behavior when you try to print it as a string. 几乎总是它不会指向有效的字符串,当您尝试将其作为字符串打印时会产生未定义的行为。
To do it properly, you should trait hWnd's bit's as integer and print it to some buffer as hex before showing in the message box: 要正确地执行此操作,您应该将hWnd的位作为整数进行特征化并将其作为十六进制打印到某个缓冲区,然后再显示在消息框中:
#include <sstream>
#include <cstdint>
#include <iomanip>
//.....
std::wstringstream ss;
ss << std::hex << L"0x" << std::setw(16) << std::setfill(L'0') <<
*reinterpret_cast<uint64_t*>(&hWnd) << std::endl;
MessageBox(nullptr, ss.str().c_str(), L"Hello World!",
MB_ICONINFORMATION | MB_OK | MB_DEFBUTTON1);
Notes: 笔记:
1) stringstream
is a C++-style sprintf
. 1) stringstream
是一个C ++风格的sprintf
。 It's str()
method returns std::string
, so to get a C-style pointer you should call c_str
on it. 它的str()
方法返回std::string
,因此要获得C风格的指针,您应该在其上调用c_str
。
2) I have no Windows to check what is HWND actually. 2)我没有Windows来检查实际上是什么HWND。 So please check it's size and use appropriate integer type instead of uint64_t
. 所以请检查它的大小并使用适当的整数类型而不是uint64_t
。 It's important, as if you use a too wide type, you'll get garbage or even access violation. 重要的是,如果你使用太宽的类型,你会得到垃圾甚至访问违规。 A better approach is to use an integer type template like one discussed here . 更好的方法是使用像这里讨论的整数类型模板。
3) Probably, you need std::wstringstream
as you are using wide-char version of MessageBox. 3)你可能需要std::wstringstream
因为你正在使用宽字符版本的MessageBox。
4) Decoration. 4)装饰。 ss << *reinterpret_cast<uint64_t*>(&hWnd)
just prints raw hex digits to ss
, so to get the right format, you should fine-tune it, setting proper padding and filling character. ss << *reinterpret_cast<uint64_t*>(&hWnd)
只是将原始十六进制数字打印到ss
,因此要获得正确的格式,您应该对其进行微调,设置正确的填充和填充字符。 For example, this will cause all integers to be printed as 16-digit numbers with leading zeros: 例如,这将导致所有整数打印为带有前导零的16位数字:
ss << std::setw(16) << std::setfill(L'0') ...
where setw
and setfill
functions are from iomanip
header. 其中setw
和setfill
函数来自iomanip
标头。 Also, printing 0x
prefix is your job, not stringstream
's. 另外,打印0x
前缀是你的工作,而不是stringstream
的。 Also take a look at std::showbase
. 另请std::showbase
。
A somewhat hackish solution that works for integers is to cast the type to (void *)
iE a pointer to void type. 一个对整数有效的hackish解决方案是将类型转换为(void *)
iE指向void类型的指针。 On current Microsoft compilers, this nicely prints it prefixed with 0x
because it is interpreted as "address". 在当前的Microsoft编译器上,这很好地打印前缀为0x
因为它被解释为“地址”。
int main(){
HWND hWnd = FindWindow(L"Notepad", L"Untitled - Notepad");
std::wstringstream wss;
wss << (void*)hWnd;
MessageBox(NULL, wss.str().c_str(), L"Hello World!", MB_ICONINFORMATION | MB_OK | MB_DEFBUTTON1);
}
This trick works out-of-the-box with Microsoft Visual C++ compilers. 这个技巧与Microsoft Visual C ++编译器开箱即用。 Gcc and clang may issue a warning which can be suppressed if really necessary (probably -Wint-to-pointer-cast
). Gcc和clang可以发出警告,如果真的有必要可以被抑制(可能是-Wint-to-pointer-cast
)。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.