объяснить этот макрос - PullRequest
0 голосов
/ 11 мая 2010
#define __T(x)      L ## x

Найден в коде из одного исходного файла заголовка MFC. Он в основном используется для преобразования строк в ........ (я не знаю, что). Если я прав, он преобразует строки в LPCTSTR ... тоже не знаю, что это за тип ...

Я не могу конвертировать char * в LPCTSTR. При обработке файла MFC следующий код всегда будет возвращать ошибку при попытке открыть файл ...

    char* filepath = "C:\\Program Files\\Microsoft Office\\Office12\\BITMAPS\\STYLES\\GLOBE.WMF";

    if( !file.Open((LPCTSTR)filepath , CFile::modeRead, &fexp) )
    {
        fexp.ReportError();
        return 1;
    }

Но вместо этого, если я напишу это так, это не выдаст ошибку:

    if( !file.Open( _T("C:\\Program Files\\Microsoft Office\\Office12\\BITMAPS\\STYLES\\GLOBE.WMF") , CFile::modeRead, &fexp) )
    {
        fexp.ReportError();
        return 1;
    }

Я смотрю на передачу переменной в качестве первого аргумента методу CFile :: Open ().

Ответы [ 3 ]

2 голосов
/ 11 мая 2010

Оператор ## является оператором конкатенации препроцессора. То есть это действительный код:

#define DECLARE_PTR(X) typedef std::auto_ptr<X> X##Ptr
DECLARE_PTR(int); // gets expanded to typedef std::auto_ptr<int> intPtr
intPtr i(new int(1));

В вашем случае макрос _T добавляет символ преобразования Long (L) к заданному входу. Это работает только со строковыми литералами. Это означает, что вы не можете написать

char* str = "ABC";
wchar_t* wstr = _T(str); // error: Lstr is undefined

но вы можете смело писать

char* str = "ABC";
LPTSTR wstr = _T("ABC"); // OK, gets expanded to wchar_t * wstr = L"ABC";
                         // when UNICODE is defined
                         // and char * wstr = "ABC"; when unicode is not defined

Оператор L является преобразователем литералов char и char * в представление Long (от представления byte в целом к ​​представлению sizeof(wchar_t) в целом).

1 голос
/ 11 мая 2010

_T() позволяет вам настроить строковые литералы, чтобы вы могли создавать как Unicode, так и не Unicode.

В сборках, отличных от Юникода, он ничего не оценивает, поэтому строковый литерал представляется как "XYZ", который является обычной узкой строкой. В сборке Unicode он оценивается как L (L"XYZ"), что говорит компилятору, что строковый литерал является строкой широких символов. Это и различные "T" строки typedefs LPCTSTR и т. Д. Позволяют вам писать код, который собирается правильно для сборок Unicode и не Unicode.

Обратите внимание, что Google - ваш друг, просто набрав _T в Google, вы получите несколько полезных результатов ...

1 голос
/ 11 мая 2010

Макрос просто записывает в строку L с аргументом, так что:

_T("xyz")

становится:

L"xyz"

Это способ сделать wstring, но в версиях, не поддерживающих Юникод, _T будет отображаться на ноль, поэтому вы получите обычные строки там.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...