Предупреждение C4251 при создании DLL, которая экспортирует класс, содержащий член ATL:: CString
Я конвертирую статическую библиотеку на основе ATL в DLL и получаю следующее предупреждение для любых экспортированных классов, которые используют класс ATL CString
(найденный в atlstr.h):
предупреждение C4251: 'Foo:: str_': class 'АТЛ:: CStringT' необходимо использовать dll-интерфейс клиентами класса "Foo"
Я правильно объявляю класс Foo
как экспортированный через __declspec(dllexport)
. Является ли это предупреждением, которое я могу смело игнорировать, или я делаю что-то неправильно? Параметры проекта DLL настроены на динамическую связь с ATL, но это, похоже, не имеет никакого значения.
Например:
#ifdef DLLTEST_EXPORTS
#define DLLTEST_API __declspec(dllexport)
#else
#define DLLTEST_API __declspec(dllimport)
#endif
// This class is exported from the DLLTest.dll
class DLLTEST_API Foo
{
public:
Foo();
CString str_; // WARNING C4251 HERE
};
Все клиенты этой DLL также будут использовать ATL.
Ответы
Ответ 1
Эта тема дает то, что я считаю лучшим ответом, Даг Харрисон (VC++ MVP):
[Это предупреждение] выдается при использовании неэкспортированный класс X в dllexported класс Y. Что так плохо об этом? Ну, предположим, у Y есть встроенная функция y_f, которая вызывает функция x_f, принадлежащая X, то есть не также встроенный. Если y_f встроен внутри какого-то клиента, который не статически ссылка X, ссылка потерпит неудачу, потому что x_f не будет найден.
Ответ 2
Эта страница Microsoft помогла мне в этом.
Как экспортировать создание экземпляра класса Standard Template Library (STL) и класса, который содержит член данных, который является объектом STL
Ответ 3
Вот нить с хорошим обсуждением этого.
Короче говоря, компилятор предупреждает вас, что, фактически, ваш экспортированный класс не отделяет интерфейс от реализации. Если члены, о которых идет речь, не доступны для клиентов, сделайте их закрытыми и #pragma
запустите предупреждение для этого члена/класса. Если участники доступны и используются клиентами, вам необходимо будет предоставить косвенный доступ к членам через аксессуар и мутаторы.
Ответ 4
Я обычно получаю это предупреждение, когда делаю глупую ошибку при построении DLL с библиотекой времени исполнения Single/Multithreaded вместо Single/MultithreadedDLL. Вы можете проверить это в настройках вашего проекта.