Чтение онлайн

на главную - закладки

Жанры

Освой самостоятельно С++ за 21 день.

Либерти Джесс

Шрифт:

Печать промежуточных значений

Не исключено, что в дополнение к возможности с помощью макроса assert убедиться в истинности некоторого тестируемого выражения вы захотите вывести на экран текущие значения указателей, переменных и строк. Это может быть полезно для проверки ваших предположений насчет некоторых аспектов работы программы, а также при поиске ошибок в циклах. Реализация этой идеи показана в листинге 21.6.

Листинг 21.6.

Вывод значений в режиме отладки

1: // Листинг 21.6. Вывод значений в режиме отладки

2: #include <iostream.h>

3: #define DEBUG

4:

5: #ifndef DEBUG

6: #define PRINT(x)

7: #else

8: #define PRINT(x) \

9: cout << #x << ":\t" << x << endl;

10: #endif

11:

12: enum bool { FALSE, TRUE } ; 13:

14: int main

15: {

16: int x = 5;

17: long у = 738981;

18: PRINT(x);

19: for (int i = 0; i < x; i++)

20: {

21: PRINT(i);

22: }

23:

24: PRINT (у);

25: PRINT("Hi,");

26: int *px = &x;

27: PRINT(px);

28: PRINT (*px);

29: return 0;

30: }

Результат:

x: 5

i: 0

i: 1

i: 2

i: 3

i: 4

у: 73898

"Hi.": Hi.

px: 0x2100

*px: 5

Анализ: Макрос PRINT(x) (строки 5—10) реализует вывод текущего значения переданного параметра. Обратите внимание, что сначала объекту cout передается сам параметр, взятый в кавычки, т.е., если вы передадите параметр x, объект cout примет "x".

Затем объект cout принимает заключенную в кавычки строку ":\t", которая обеспечивает печать двоеточия и табуляции. После этого объект cout принимает значение параметра (x), а объект endl выполняет переход на новую строку и очищает буфер.

Обратите внимание, что у вас вместо значения 0x2100 может быть выведено другое число.

Уровни отладки

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

Чтобы определить уровень отладки, достаточно после выражения #define DEBUG указать номер. Хотя число уровней может быть любым, обычная система должна иметь четыре уровня: HIGH (высокий), MEDIUM (средний), LOW (низкий) и NONE (никакой).

В листинге 21.7 показано, как это можно сделать, на примере классов String и Animal из листинга 21.5.

Листинг 21.7. Уровни отладки

1: enum LEVEL { NONE, LOW, MEDIUM, HIGH } ;

2: const int FALSE = 0;

3: const int TRUE = 1;

4: typedef int bool;

5:

6: #define DEBUGLEVEL HIGH

7:

8: #include <iostream.h>

9: #include <string.h>

10:

11: #if DEBUGLEVEL < LOW // должен быть средний или высокий

12: #define ASSERT(x)

13: #else

14: #define ASSERT(x)

15: if (!(x))

16: {

17: cout << "ERROR!! Assert " << #x << " failed\n";

18: cout << " on line " << __LINE__ << "\n";

19: cout << " in file " << FILE << "\n";

20: }

21: #endif

22:

23: #if DEBUGLEVEL < MEDIUM

24: #define EVAL(x)

25: #else

26: #define EVAL(x)

27: cout << #x << ":\t" << x << andl;

28: #endif

29:

30: #if DEBUGLEVEL < HIGH

31: #define PRINT(x)

32: #else

33: #define PRINT(x)

34: cout << x << endl;

35: #endif

36:

37:

38: class String

39: {

40: public:

41: // конструкторы

42: String;

43: String(const char *const);

44: String(const String &);

45: ~String;

46:

47: char & operator[](int offset);

48: char operator[](int offset) const;

49:

50: String & operator= (const String &);

51: int GetLenconst { return itsLen; }

52: const char >> GetString const

53: { return itsString; }

54: bool Invariants const;

55:

56: private:

57: String (int); // закрытый конструктор

58: char * itsString;

59: unsigned short itsLen;

60: };

61:

62: // стандартный конструктор создает строку нулевой длины

63: String::String

64: {

65: itsString = new char[1];

66: itsString[0] = '\0';

67: itsLen=0;

68: ASSERT(Invariants);

69: }

70:

71: // закрытый (вспомогательный) конструктор, используемый

72: // методами класса только для создания новой строки

73: // требуемого размера. Заполняется символом Null.

74: String::String(int len)

75: {

76: itsString = new char[len+1];

77: for (int i = 0; i<=len; i++)

78: itsString[i] = '\0';

Поделиться:
Популярные книги

Лишняя дочь

Nata Zzika
Любовные романы:
любовно-фантастические романы
8.22
рейтинг книги
Лишняя дочь

Свет Черной Звезды

Звездная Елена
6. Катриона
Любовные романы:
любовно-фантастические романы
5.50
рейтинг книги
Свет Черной Звезды

Студиозус

Шмаков Алексей Семенович
3. Светлая Тьма
Фантастика:
юмористическое фэнтези
городское фэнтези
аниме
5.00
рейтинг книги
Студиозус

Боец с планеты Земля

Тимофеев Владимир
1. Потерявшийся
Фантастика:
боевая фантастика
космическая фантастика
5.00
рейтинг книги
Боец с планеты Земля

Клан

Русич Антон
2. Долгий путь домой
Фантастика:
боевая фантастика
космическая фантастика
5.60
рейтинг книги
Клан

Одна тень на двоих

Устинова Татьяна Витальевна
Детективы:
прочие детективы
9.08
рейтинг книги
Одна тень на двоих

Часовое имя

Щерба Наталья Васильевна
4. Часодеи
Детские:
детская фантастика
9.56
рейтинг книги
Часовое имя

Кодекс Крови. Книга IХ

Борзых М.
9. РОС: Кодекс Крови
Фантастика:
фэнтези
попаданцы
аниме
5.00
рейтинг книги
Кодекс Крови. Книга IХ

Идеальный мир для Лекаря

Сапфир Олег
1. Лекарь
Фантастика:
фэнтези
юмористическое фэнтези
аниме
5.00
рейтинг книги
Идеальный мир для Лекаря

Я тебя верну

Вечная Ольга
2. Сага о подсолнухах
Любовные романы:
современные любовные романы
эро литература
5.50
рейтинг книги
Я тебя верну

Чужая семья генерала драконов

Лунёва Мария
6. Генералы драконов
Фантастика:
фэнтези
5.00
рейтинг книги
Чужая семья генерала драконов

Лекарь для захватчика

Романова Елена
Фантастика:
попаданцы
историческое фэнтези
фэнтези
5.00
рейтинг книги
Лекарь для захватчика

Санек

Седой Василий
1. Санек
Фантастика:
попаданцы
альтернативная история
4.00
рейтинг книги
Санек

Купи мне маму!

Ильина Настя
Любовные романы:
современные любовные романы
5.00
рейтинг книги
Купи мне маму!