【问题标题】:LPCTSTR to LPCSTR conversionLPCTSTR 到 LPCSTR 的转换
【发布时间】:2014-01-17 00:41:22
【问题描述】:

我正在尝试使用GetFileInformationByHandle() 获取现有文件的信息。我执行所需任务的函数接收LPCTSTR Filename 作为参数。代码如下:

getfileinfo(LPCTSTR Filename)
{
    OFSTRUCT oo;
    BY_HANDLE_FILE_INFORMATION lpFileInformation;
    HFILE hfile=OpenFile((LPCSTR)Filename,&oo,OF_READ);
    int err=GetLastError();
    GetFileInfomationByHandle((HANDLE)hfile,&lpFileInformation);
}

如果我将Filename 声明为LPCSTR,则上面的代码可以正常工作,但是根据我的函数要求,我在LPCTSTR 中收到文件名,所以如果我使用类型转换,那么openfile() 找不到指定的文件并返回-1 .

如果文件名是LPCTSTR,谁能告诉我如何获取文件信息?或者如何将LPCTSTR 转换为LPCSTR

为什么这种类型转换不起作用?我相信这应该可行。

【问题讨论】:

  • 取消TCHARs 并使用所有 Windows API 函数的宽字符串版本。
  • 这里的问题是 OpenFile 的宽字符串版本不存在。
  • 假设您的建筑定义了 UNICODE;您所有的 LPCTSTR 在编译时实际上都是 LPWSTR (WCHAR)。因此,在 LPCTSTR 上转换的 LPCSTR 类型通常会被解释为(由为 LPCSTR 设计的东西)解释为单个 ASCII 字符后跟 0x00 字节。你会度过一段糟糕的时光。

标签: c++ string winapi file-handling


【解决方案1】:

解决您当前问题的方法是将OpenFile() 替换为CreateFile(),就像OpenFile() documentation 所说的那样:

注意此功能功能有限,不推荐使用。对于新的应用程序开发,请使用 CreateFile 函数。

例如:

getfileinfo(LPCTSTR Filename)
{
    HANDLE hFile = CreateFile(FileName, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, 0, NULL);
    if (hFile == INVALID_HANDLE_VALUE)
    {
        int err = GetLastError();
        // handle error as needed ...
    }
    else
    {
        BY_HANDLE_FILE_INFORMATION FileInfo = {0};
        BOOL ok = GetFileInformationByHandle(hFile, &FileInfo);
        int err = GetLastError();
        CloseHandle(hFile);

        if (!ok)
        {
            // handle error as needed ...
        }
        else
        {
            // use FileInfo as needed...
        }
    }
}

话虽如此,更好的解决方案是根本不打开文件。 GetFileInformationByHandle()返回的大部分信息都可以使用FindFirstFile()来获取:

getfileinfo(LPCTSTR Filename)
{
    WIN32_FIND_DATA FileData = {0};
    HANDLE hFile = FindFirstFile(Filename, &FileData);
    if (hFile == INVALID_HANDLE_VALUE)
    {
        int err = GetLastError();
        // handle error as needed ...
    }
    else
    {
        FindClose(hFile);
        // use FileData as needed ...
    }
}

【讨论】:

    【解决方案2】:

    查看项目属性/配置属性/常规/字符集。这通常设置为 UNICODE。可以改为MBCS。

    如果设置为MBCS,则代码不需要修改。

    如果它设置为 Unicode,我怀疑你不会问这个问题,使用 widechartomultibyte 将它从 LPCTSTR (const wchar_t*) 转换为 LPSTR (const char*)。

    【讨论】:

      【解决方案3】:

      仅转换指针不会将被指向的实际数据(即文件名)更改为 8 位字符。

      阅读the docs at MSDN 建议改用CreateFile,它处理LPCTSTR 文件名。

      【讨论】:

        猜你喜欢
        • 2010-09-24
        • 2010-12-11
        • 1970-01-01
        • 2017-11-10
        • 2016-06-07
        • 2018-06-02
        • 1970-01-01
        • 2010-11-01
        • 1970-01-01
        相关资源
        最近更新 更多