C / C++ номер строки



в целях отладки, я могу получить номер строки C/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)
1623   7  

7 ответов:

вы должны использовать макрос __LINE__ и __FILE__. Это предопределенные макросы и часть стандарта C/C++. Во время предварительной обработки они заменяются соответственно постоянной строкой, содержащей целое число, представляющее текущий номер строки, и текущим именем файла.

другие переменные препроцессора :

  • __func__: имя функции (это часть C99 не все компиляторы C++ поддерживают его)
  • __DATE__: a строка формы "ммм ДД гггг"
  • __TIME__: строка формы "чч: мм: СС"

ваш код будет :

if(!Logical)
  printf("Not logical value at line number %d in file %s\n", __LINE__, __FILE__);

в рамках стандарта C++ существует несколько предопределенных макросов, которые можно использовать. Раздел 16.8 стандарта C++ определяет, среди прочего,__LINE__ макрос.

__LINE__: номер строки текущей исходной строки (десятичное число постоянный.)
__FILE__: предполагаемое имя исходного файла (символьная строка буквальный.)
__DATE__: дата перевода исходного файла (a символьная строка буквальный...)
__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. Вот пример main:

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) Перед exampleMethod ()...
пример (главный.cpp: 7) printf () синтаксис: string = foobar, int = 42
основной(main.cpp: 13) успех!

использовать __LINE__ (это двойное подчеркивание строки с двойным подчеркиванием), препроцессор заменит его номером строки, на которой он встречается.

оформить заказ __FILE__ и __LINE__ макрос

попробовать __FILE__ и __LINE__.
Вы также можете найти __DATE__ и __TIME__ полезное.
Хотя, если вам не нужно отлаживать программу на стороне клиента и, следовательно, нужно регистрировать эти сведения, вы должны использовать обычную отладку.

Так как я также столкнулся с этой проблемой сейчас, и я не могу добавить ответ на другой, но также действительный вопрос, заданный здесь, я приведу пример решения проблемы: получение только номера строки, где функция была вызвана в C++ с помощью шаблонов.

Background: в 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, это может быть очень интересной альтернативой, чем использование макросов для получения вызывающей линии.

Comments

    Ничего не найдено.