2016-01-27 2 views
2

У меня возникли проблемы с использованием функции SHGetKnownFolderPath(). Я получаю следующее сообщение об ошибке: Type error in argument 1 to 'SHGetKnownFolderPath'; expected 'const struct _GUID *' but found 'struct _GUID'.Не удается получить функцию SHGetKnownFolderPath()

В KnowFolders.h мы имеем следующие соответствующие определения:

#define DEFINE_KNOWN_FOLDER(name,l,w1,w2,b1,b2,b3,b4,b5,b6,b7,b8) \ 
    EXTERN_C const GUID name 
... 
DEFINE_KNOWN_FOLDER(FOLDERID_ProgramFiles,0x905e63b6,0xc1bf,0x494e,0xb2,0x9c,0x65,0xb7,0x32,0xd3,0xd2,0x1a); 

Я использую Pelles C компилятор.

Это мой пример кода:

#include <windows.h> 
#include <wchar.h> 
#include <KnownFolders.h> 
#include <shlobj.h> 

int wmain(int argc, wchar_t **argv) { 

    PWSTR path = NULL; 

    HRESULT hr = SHGetKnownFolderPath(FOLDERID_ProgramFiles, 0, NULL, &path);  

    if (SUCCEEDED(hr)){ 

     wprintf(L"%ls", path); 
    } 

    CoTaskMemFree(path); 

    return 0; 
} 

Как исправить это сообщение об ошибке?

EDIT Я нашел примеры кода с SHGetKnownFolderPath(); все выполняют функцию без указателя. Например:

hr = SHGetKnownFolderPath(FOLDERID_Public, 0, NULL, &pszPath); 
if (SUCCEEDED(hr)) 
{ 
    wprintf(L"FOLDERID_Public: %s\n", pszPath); 
    CoTaskMemFree(pszPath); 
} 

CppShellKnownFolders.cpp

+3

Он хочет указатель на GUID, поэтому передать его указатель. 'SHGetKnownFolderPath (& FOLDERID_ProgramFiles, ...);' –

+3

Сообщение об ошибке вряд ли может быть более ясным. В нем говорится: * Введите ошибку в аргументе 1 в 'SHGetKnownFolderPath'; ожидаемый 'const struct _GUID *', но нашел 'struct _GUID' * Это не могло быть сделано более ясным. Я полагаю, вы понимаете концепцию несоответствия типа? –

+0

@JonathanPotter Уже пробовал. Приводит к неразрешенному внешнему символу «FOLDERID_ProgramFiles». ошибка.Кроме того, рабочие примеры, которые я нашел, не передают указатель. –

ответ

5

С помощью замечания Джонатана Поттера, я был в состоянии исправить пример.

Проблема была очень тонкой. Следующая строка кода выглядит как C, но это на самом деле C++.

HRESULT hr = SHGetKnownFolderPath(FOLDERID_Documents, 0, NULL, &path);

SHGetKnownFolderPath() функция имеет следующий прототип:

STDAPI SHGetKnownFolderPath(REFKNOWNFOLDERID, DWORD, HANDLE, PWSTR*);

Ее первым аргументом является REFKNOWNFOLDERID.

В shtypes.h файле мы находим следующее:

#ifdef __cplusplus 
#define REFKNOWNFOLDERID const KNOWNFOLDERID & 
#else 
#define REFKNOWNFOLDERID const KNOWNFOLDERID * /*__MIDL_CONST*/ 
#endif /* __cplusplus */ 

Это означает, что в C++ REFKNOWNFOLDERID является справочным и в C это указатель. Как следствие, нам не нужен амперсанд в коде C++ для первого параметра. В Visual C++ C код часто скомпилирован с C++, а различие между языками часто размыто.

Вторая проблема, ошибка Unresolved external symbol 'FOLDERID_ProgramFiles'. error. устраняется добавлением #include <initguid.h> до #include <ShlObj.h>. Причина объясняется в этом article.

Таким образом, следующий код компилирует на Пеллес C.

#include <windows.h> 
#include <initguid.h> 
#include <KnownFolders.h> 
#include <ShlObj.h> 
#include <wchar.h> 

int wmain(void) { 

    PWSTR path = NULL; 

    HRESULT hr = SHGetKnownFolderPath(&FOLDERID_Documents, 0, NULL, &path); 

    if (SUCCEEDED(hr)) { 
     wprintf(L"%ls\n", path); 
    } 

    CoTaskMemFree(path); 

    return 0; 
}