Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/image-processing/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Winapi 在Win32中,如何成功地将文本文件读入内存?_Winapi - Fatal编程技术网

Winapi 在Win32中,如何成功地将文本文件读入内存?

Winapi 在Win32中,如何成功地将文本文件读入内存?,winapi,Winapi,我试图让简单的文件IO在Win32中工作。到目前为止,编写工作正常,但读取工作不正常:虽然它成功地读取了内容,但在字符串中附加了额外的“垃圾”。到目前为止,我的代码如下。该程序已定义了UNICODE 写作: DWORD dwTextSize = GetWindowTextLength(hWndTextBox); WCHAR *lpszText = new WCHAR[dwTextSize]; GetWindowText(hWndTextBox, lpszText, dwTextSize + 1)

我试图让简单的文件IO在Win32中工作。到目前为止,编写工作正常,但读取工作不正常:虽然它成功地读取了内容,但在字符串中附加了额外的“垃圾”。到目前为止,我的代码如下。该程序已定义了
UNICODE

写作:

DWORD dwTextSize = GetWindowTextLength(hWndTextBox);
WCHAR *lpszText = new WCHAR[dwTextSize];
GetWindowText(hWndTextBox, lpszText, dwTextSize + 1);
hTextFile = CreateFile(lpszTextFileName, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
DWORD dwBytesWritten;
WriteFile(hTextFile, lpszText, 2 * dwTextSize, &dwBytesWritten, NULL);  // x2 for 2 bytes per Unicode character
CloseHandle(hTextFile);
DeleteObject(hTextFile);
对于这个例子,
你好,世界已成功保存为
你好,世界

阅读:

lpszTextFileName = L"text.txt";        // LPCTSTR Variable
hTextFile = CreateFile(lpszTextFileName, GENERIC_READ, 0, NULL, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
DWORD dwFileSize = GetFileSize(hTextFile, &dwFileSize);
DWORD dwBytesRead;
WCHAR *lpszText = new WCHAR[dwFileSize / 2];
ReadFile(hTextFile, lpszText, dwFileSize, &dwBytesRead, NULL);
CloseHandle(hTextFile);
然后,该字符串用于设置编辑控件的文本:

SendMessage(hWndTextBox, WM_SETTEXT, NULL, (LPARAM)lpszText);    // SetWindowText() also possible
你好,世界被读回,它读回为
你好,世界!﷽﷽ꮫꮫꮫꮫﻮ
或其视觉变体,但基本上是“垃圾”


我可能错过了一些相当明显的东西,但我看不到在哪里!这个问题有解决方案吗?如果有,是什么解决方案?

好的,我是以一个评论开始的,但是它失去了控制

用于写作

这:

应该是:

WCHAR *lpszText = new WCHAR[dwTextSize+1];
这:

根本不应该在那里。。摆脱它

我假设您
delete[]lpszText完成后的某个地方。如果没有,请这样做


用于阅读

GetFileSize()
的第二个参数不应与返回值相同。对于大文件大小,它是64位值中的高32位。如果您知道您的文件大小小于4gB,则可以将其保留为空,因此请更改以下内容:

DWORD dwFileSize = GetFileSize(hTextFile, &dwFileSize);
为此:

DWORD dwFileSize = GetFileSize(hTextFile, NULL);
您必须说明文件缓冲区的null终止符,因此:

WCHAR *lpszText = new WCHAR[dwFileSize / 2];
应改为:

WCHAR *lpszText = new WCHAR[dwFileSize / 2 + 1];
lpszText[dwFileSize / 2] = 0;

其余的应该像你希望的那样起作用。没有错误检查,这是不好的,但我见过更糟的。和以前一样,我假设您
delete[]lpszText完成后的某个地方。如果没有,请执行此操作。

Null在将字符串发送到
SendMessage()
之前终止字符串(并确保为该终止符分配空间)。(如果不明显,请在处理完缓冲区后将其删除)。另外,
GetWindowText(hWndTextBox、lpszText、dwTextSize+1)
放入前一行分配为
dwTextSize
的缓冲区可能不是一个明智的主意。如何在Win32中以null终止字符串?它只是类似于
lpszText[sizeof(lpszText)-1]=(WCHAR)0;//或“\0”
?将字符串中的第3个(或第7个,如果编译64位)wchar设置为0,这不是您想要的
sizeof(指针类型变量)
sizeof(数组类型变量)
不同。请参阅下面的帖子,了解如何终止字符串。非常好的帖子。令人惊讶的是,8行代码竟然有这么多错误/问题。。。我不知道我个人会使用
lpszText[dwFileSize/2]=0
;我更喜欢
memset
直接将缓冲区设置为全零,但这是一种风格,对于不熟悉Windows和C/C++的人来说,大多数情况都很常见。唯一让我选择“wtf???”的是
DeleteObject()
。天知道那是从哪里来的。关于
memset
,这是一个性能问题。不需要用一堆零填充内存,只需要在之后立即覆盖除一个之外的所有零。来自这样做可能会很昂贵的平台。但是,不管是什么东西,只要能让你在晚上睡觉,DeleteObject就很特别了。至于
memset
,我知道你的来历了——我也是一个非常注重性能的极客,唉,这是我们工作场所的一项要求……太完美了——非常感谢你的帮助!是-删除了
lpszText
变量,但我忽略了代码。我主要是一名.NET开发人员,但我决定尝试一些Win32进行实验/学习练习,因此犯了很多错误,但我正在逐步做到这一点@哈泽尔,你做得很好。在编写API调用之前,只需仔细、彻底地理解API调用(即阅读其文档)。与.NET不同,C/C++WIN32 API编程有点不可原谅。在一句话中,“不能让你变得更强的东西会杀死你。”“sorta way=P
WCHAR *lpszText = new WCHAR[dwFileSize / 2];
WCHAR *lpszText = new WCHAR[dwFileSize / 2 + 1];
lpszText[dwFileSize / 2] = 0;