Номер линии C / C ++
-
27-09-2019 - |
Вопрос
Ради целей отладки, могу ли я получить номер линии в Слияние/ C ++ компиляторы? (стандартный способ или конкретные способы определенных компиляторов)
например
if(!Logical)
printf("Not logical value at line number %d \n",LineNumber);
// How to get LineNumber without writing it by my hand?(dynamic compilation)
Решение
Вы должны использовать макрос препроцессора __LINE__
а также __FILE__
. Отказ Они являются предопределенными макросами и частью стандарта C / C ++. Во время предварительной обработки они заменяются соответственно постоянной строкой, содержащим целое число, представляющее текущий номер строки и текущим именем файла.
Другие препроцессорные переменные:
__func__
: имя функции (это часть C99., не все компиляторы C ++ поддерживают его)__DATE__
: строка формы "ммм dd yyyy"__TIME__
: строка формы "HH: мм: ss"
Ваш код будет:
if(!Logical)
printf("Not logical value at line number %d in file %s\n", __LINE__, __FILE__);
Другие советы
В рамках стандарта C ++ существует некоторые заранее определенные макросы, которые вы можете использовать. Раздел 16.8 стандарта C ++ определяет среди прочего, __LINE__
макрос
__LINE__
: Номер строки текущей исходной линии (десятичная константа).
__FILE__
: Предполагаемое имя исходного файла (символьный строковый литерал).
__DATE__
: Дата перевода исходного файла (символьный строковый литерал ...)
__TIME__
: Время перевода исходного файла (символьный строковый литерал ...)
__STDC__
: Будь то__STDC__
предопределен
__cplusplus
: Имя__cplusplus
определяется значением 199711L при составлении единицы перевода C ++
Так что ваш код будет:
if(!Logical)
printf("Not logical value at line number %d \n",__LINE__);
Вы можете использовать макрос с тем же поведением, что и printf (), За исключением того, что он также содержит информацию о отладке, такой как имя функции, класс и номер строки:
#include <cstdio> //needed for printf
#define print(a, args...) printf("%s(%s:%d) " a, __func__,__FILE__, __LINE__, ##args)
#define println(a, args...) print(a "\n", ##args)
Эти макросы должны вести себя одинаково printf (), в том числе Java Stacktrace - как информация. Вот пример Главная:
void exampleMethod() {
println("printf() syntax: string = %s, int = %d", "foobar", 42);
}
int main(int argc, char** argv) {
print("Before exampleMethod()...\n");
exampleMethod();
println("Success!");
}
Который приводит к следующему выпуску:
Main (Main.CPP: 11) Перед экзаменомethod () ...
ExampleMethod (Main.cpp: 7) PrintF () Синтаксис: string = foobar, int = 42
Main (Main.cpp: 13) Успех!
Использовать __LINE__
(Это двойная подчеркивание линии двойной подчеркивания), препроцессор заменит его с номером линии, на котором он встречается.
Проверить __FILE__
а также __LINE__
макрос
Пытаться __FILE__
а также __LINE__
.
Вы можете также найти __DATE__
а также __TIME__
полезный.
Хотя, если вы не отладки программы на клиентах, и поэтому нужно регистрировать эту информацию, вы должны использовать обычную отладку.
Так как я также сталкиваюсь с этой проблемой, и я не могу добавить ответ на другую, но и действующий вопрос заданный вопрос здесьЯ предоставлю пример решения проблемы: Получение только номера строки, где функция была вызвана в C ++ с использованием шаблонов.
Фон: в C ++ можно использовать целочисленные значения не типа в качестве аргумента шаблона. Это отличается от типичного использования типов данных в качестве аргументов шаблонов. Таким образом, идея состоит в том, чтобы использовать такие целочисленные значения для вызова функции.
#include <iostream>
class Test{
public:
template<unsigned int L>
int test(){
std::cout << "the function has been called at line number: " << L << std::endl;
return 0;
}
int test(){ return this->test<0>(); }
};
int main(int argc, char **argv){
Test t;
t.test();
t.test<__LINE__>();
return 0;
}
Выход:
Функция была вызвана по номеру строки: 0
Функция была вызвана по номеру строки: 16
Вот одно упомянутое здесь, так это то, что в стандарте C ++ 11 можно дать значения шаблона по умолчанию для функций с использованием шаблона. В Pre C ++ 11 значения по умолчанию для не типа аргументов, кажется, работают только для аргументов класса шаблонов. Таким образом, в C ++ 11 не нужно было бы иметь дублирующие определения функций, как указано выше. В C ++ 11 его также действует, чтобы иметь Const Char * шаблон аргументов, но его невозможно использовать их с помощью литералов, таких как __FILE__
или __func__
как уже упоминалось здесь.
Поэтому в конце концов, если вы используете C ++ или C ++ 11, это может быть очень интересной альтернативой, чем использование макроса, чтобы получить вызов.