Как я могу использовать #pragma message (), чтобы сообщение указывало на файл (lineno)? - PullRequest
30 голосов
/ 11 мая 2011

Чтобы добавить элементы todo в мой код, я хочу поместить сообщение в вывод компилятора.
Мне бы хотелось, чтобы это выглядело так:

c:/temp/main.cpp(104): TODO - add code to implement this

, чтобыиспользуйте функцию вывода сборки Visual Studio, чтобы перейти к соответствующей строке, дважды щелкнув ее.

Но макрос __LINE__, кажется, расширяется до int, что запрещает запись

#pragma message( __FILE__ "("__LINE__"): ..." )

Был бы другой путь?

Ответы [ 6 ]

38 голосов
/ 11 мая 2011

Вот тот, который позволяет вам щелкнуть на панели вывода:

(там также есть и другие полезные советы)

http://www.highprogrammer.com/alan/windev/visualstudio.html

 // Statements like:
 // #pragma message(Reminder "Fix this problem!")
 // Which will cause messages like:
 // C:\Source\Project\main.cpp(47): Reminder: Fix this problem!
 // to show up during compiles. Note that you can NOT use the
 // words "error" or "warning" in your reminders, since it will
 // make the IDE think it should abort execution. You can double
 // click on these messages and jump to the line in question.

 #define Stringize( L )     #L 
 #define MakeString( M, L ) M(L)
 #define $Line MakeString( Stringize, __LINE__ )
 #define Reminder __FILE__ "(" $Line ") : Reminder: "

После определения использовать так:

#pragma message(Reminder "Fix this problem!") 

Это создаст вывод как:

C: \ Source \ Project \ main.cpp (47): Напоминание: исправьте эту проблему!

7 голосов
/ 11 мая 2011

только что сделал это, и это, безусловно, превосходит мое старое решение использования #error: D

#define _STR(x) #x
#define STR(x) _STR(x)
#define TODO(x) __pragma(message("TODO: "_STR(x) " :: " __FILE__ "@" STR(__LINE__)))

, вы можете изменить это так, как вам нравится / в соответствии с вашими потребностями.Пример его использования:

//in code somewhere
TODO(Fix this);

вывод на панели консоли:

1>TODO: Fix this :: c:\users\administrator\documents\visual studio 2008\projects\metatest\metatest\metatest.cpp@33

Единственный недостаток - вы не можете перейти к этой строке (дважды щелкнув сообщение впанель консоли) с использованием __pragma (но при тестировании с #pragma, похоже, это не так ...)

2 голосов
/ 06 апреля 2012

Это дополнение к ответу для тех, кто считает утомительным вводить директивы #pragma каждый раз, когда им нужно поставить закладку в коде: вы можете сохранить несколько нажатий клавиш, взбивая макрос для этого для тебя! Хотя в целом у вас не может быть директивы #pragma в макросах, компиляторы MS C / C ++ версии 2008 и выше поддерживают специальное расширение для конкретного производителя, называемое __pragma, которое можно использовать с макросами. См. Директивы Прагмы и ключевое слово __Pragma .

Я ежедневно использую что-то похожее на следующее:

#define STR2(x) #x
#define STR1(x) STR2(x)
#define LOC __FILE__ "("STR1(__LINE__)") : Warning Msg: "
#define WARNING_BUILDER(x) __FILE__ "("STR1(__LINE__)") : Warning Msg: " __FUNCTION__ " requires " #x
#define WREVIEW WARNING_BUILDER(review)
#define WUT WARNING_BUILDER(unit-testing)

#ifdef SPECIAL_WARNINGS
    #ifdef SPECIAL_WARNINGS_REVIEW
        #define MARK_FOR_REVIEW() do { \
                    __pragma(message( WREVIEW )) \
                } while (0)
    #else
        #define MARK_FOR_REVIEW 
    #endif

    #ifdef SPECIAL_WARNINGS_UNIT_TEST
        #define MARK_FOR_UNIT_TEST() do { \
                    __pragma(message( WUT )) \
                } while (0)
    #else
        #define MARK_FOR_UNIT_TEST 
    #endif
#endif


// uncomment/set in build-environment to enable special warnings
//#define SPECIAL_WARNINGS
#ifdef SPECIAL_WARNINGS
// uncomment/set in build-environment if you want only code review warnings
//#define SPECIAL_WARNINGS_REVIEW
// uncomment/set in build-environment if you want only unit-test warnings
//#define SPECIAL_WARNINGS_UNIT_TEST
#endif

int main()
{
MARK_FOR_REVIEW();
MARK_FOR_UNIT_TEST();
}

Вы можете легко расширить его в соответствии с вашими потребностями и добавить больше предупреждений. Хорошая часть такой системы состоит в том, что вы можете выборочно включать, скажем, только элементы проверки кода и не беспокоиться ни о чем другом, устанавливая соответствующий макрос в настройках сборки.

1 голос
/ 06 июля 2019

В Visual C ++ вы можете просто сделать

#pragma message(__FILE__ "(" _CRT_STRINGIZE(__LINE__) ")" ": warning: [blah]")

_CRT_STRINGIZE часто уже определено в некотором заголовке, но если это не так, вы можете определить его:

#define _CRT_STRINGIZE_(x) #x
#define _CRT_STRINGIZE(x) _CRT_STRINGIZE_(x)
1 голос
/ 02 ноября 2013

Этот позволяет использовать его без #pragma (я думаю, что это специфично для Microsoft), и когда вы нажимаете, он переносит вас на строку, так как показывает номер файла и строки так же, как и обычное сообщение об ошибке / предупреждение, поскольку ни одно издругие, кажется, делают это.Раньше это работало без __pragma, но более новые версии msvc требуют этого.Я использую его с 90-х годов.Я использую Visual Studio 2013

#define MacroStr(x)   #x
#define MacroStr2(x)  MacroStr(x)
#define Message(desc) __pragma(message(__FILE__ "(" MacroStr2(__LINE__) ") :" #desc))

пример:

Message("Need to add unit testing here")

вывод: 1> c: \ source \ include \ mithrilsoftware.h (180): «Необходимо добавить модульное тестирование здесь«

0 голосов
/ 11 мая 2011

Используйте токен # . Я разместил пример из MSDN ниже:

// collisions.h
#define __STR2__(x) #x
#define __STR1__(x) __STR2__(x)
#define __LOC__ __FILE__ "("__STR1__(__LINE__)") : Warning Msg: "

// collisions.cpp
#pragma message(__LOC__"Need to do 3D collision testing")
...