Eksportowanie klasy String przy użyciu CStringT
W przeszłości MFC deweloperzy mają pochodzące z CString do specialize własne klasy string.W Microsoft Visual C++ .net (MFC 8.0) CString klasy został zastąpiony przez szablon klasy o nazwie CStringT.To kilku świadczeń:
Dozwolone MFC CString klasy do wykorzystania w ATL projektów bez łączenia większych statyczne biblioteki MFC lub DLL.
Nowe CStringT klasy szablonu można dostosować CString zachowanie przy użyciu parametrów szablonu, które określają cechy znaków, podobne do szablonów w bibliotece szablon standardowy (STL).
Podczas eksportowania klasy string DLL korzystania z CStringT, kompilator automatycznie wywóz CString klasa podstawowa.Ponieważ CString jest sama klasa szablonu, to może zostać zrealizowane przez kompilator, gdy jest używany, chyba że jest świadomy kompilator, CString importowanym z biblioteki DLL.Po przeprowadzeniu migracji projektów programu Visual C++ 6.0 do programu Visual C++ .net, może być przejrzane linker symbol błędy pomnożyć zdefiniowane CString z powodu kolizji z CString przywożonych z biblioteki DLL i wersji lokalnie skonkretyzowanym.Właściwy sposób, w tym opisano poniżej.Aby uzyskać więcej informacji na ten temat, zobacz artykuł bazy wiedzy Knowledge Base "łączenie błędy podczas importowania pochodnych CString klasy" (Q309801) MSDN Library CD-ROM lub na https://support.microsoft.com/default.aspx.
Następujący scenariusz spowoduje, że program łączący do wyprodukowania symbol błędy mnożenie zdefiniowanych klas.Załóżmy, że eksportowane są CString-klasy (CMyString) z rozszerzeniem MFC DLL:
// MyString.h
class AFX_EXT_CLASS CMyString : public CString
{
// Your implementation code
};
Kod konsumenta używa mieszaniny CString i CMyString. "MyString.h"jest niedostępna w skompilowanych nagłówka i użycie niektórych CString nie ma CMyString widoczne.
Załóżmy, że CString i CMyString klasy w oddzielne źródło plików, Source1.cpp i Source2.cpp.W Source1.cpp, użyj CMyString i # include MyString.h.W Source2.cpp, użyj CString, ale nie # obejmują MyString.h.W takim przypadku program łączący będzie skarga dotycząca CStringT mnożenie zdefiniowany.Jest to spowodowane przez CString jest zarówno przywożone z biblioteki DLL, że wywóz CMyStringi uruchamianiu lokalnie przez kompilator poprzez CStringT szablonu.
Aby rozwiązać ten problem, wykonaj następujące czynności:
Wywóz CStringA i CStringW (i niezbędne klas podstawowych) z MFC90.DLL.MFC DLL wywożonych zawsze będzie korzystać z projektów, które zawierają MFC CStringA i CStringW, jak w poprzedniej implementacji MFC.
Następnie utwórz klasy pochodnej można eksportować przy użyciu CStringT szablonu jako CStringT_Exported jest poniżej, na przykład:
#ifdef _AFXDLL
#define AFX_EXT_CSTRING AFX_EXT_CLASS
#else
#define AFX_EXT_CSTRING
#endif
template< typename BaseType, class StringTraits >
class AFX_EXT_CSTRING CStringT_Exported
: public CStringT< BaseType, StringTraits >
{
// Reimplement all CStringT<> constructors and
// forward to the base class implementation
};
Zastąpienie poprzednich w AfxStr.h, CString, CStringA, i CStringW definicje TypeDef następujące:
typedef CStringT_Exported< wchar_t,
StrTraitMFC< wchar_t > > CStringW;
typedef CStringT_Exported< char,
StrTraitMFC< char > > CStringA;
typedef CStringT_Exported< TCHAR,
StrTraitMFC< TCHAR > > CString;
Istnieje kilka ostrzeżenia:
Nie należy eksportować CStringT sobie, ponieważ spowoduje to tylko ATL projektów do eksportowania specjalistycznej CStringT klasy.
Za pomocą eksportowalne uzyskane klasy z CStringT minimalizuje konieczności ponownej CStringT funkcji.Dodatkowy kod jest ograniczona do przekazywania konstruktorów CStringT klasa podstawowa.
CString, CStringA, i CStringW powinna być oznaczona tylko __declspec(dllexport/dllimport) podczas budowania z MFC współużytkowane biblioteki DLL.Łączenia w przypadku biblioteki MFC statycznych, należy nie zaznaczyć tych klas wywożonych; wykorzystanie inaczej, wewnętrzny CString, CStringA, i CStringW wewnątrz biblioteki DLL użytkownika spowoduje oznaczenie CString , jak również eksportowane.