<< t
не равно u.
И передадим
в конструктор runtime_error то сообщение, которое у нас получилось.
Давайте скомпилируем то, что у нас пока есть.
Отлично, оно компилируется.
У вас мог возникнуть вопрос, а почему я здесь для двух
аргументов использую разные типы: типы t и u.
Вроде как мы же сравниваем их между собой, и логично было бы,
чтобы они были одного типа.
На самом деле, так шаблон AssertEqual более удобен в использовании,
особенно когда дело доходит до целочисленных типов.
Потому что мы с вами уже знаем, что в C++ много различных
целочисленных типов, и вот для того, чтобы сравнивать,
например, int и int64_t, которые являются разными типами,
удобно передавать их с помощью разных шаблонных аргументов,
и мы посмотрим, как мы этим будем пользоваться, совсем скоро.
Давайте этот наш шаблон AssertEqual встроим в один из тестов.
И начнем мы с теста TestCount,
который проверяет, что функция GetSynonymCount,
возвращающая количество синонимов для данного слова, работает правильно.
Что мы сделаем?
Мы заменим вызов assert на наш AssertEqual,
только внутри этой функции.
И так как у нас AssertEqual
принимает два параметра, то первым параметром является
результат вызова GetSynonymCount, а вторым то число, которое мы ожидаем.
Скомпилируем наш код.
Мы с вами видим, что у нас есть
Warning, который
[БЕЗ_ЗВУКА] нам
говорит о сравнении между знаковым и беззнаковым целыми числами.
Если мы два раза по нему нажмем, то мы попадем внутрь нашего AssertEqual.
А вот здесь, если мы нажмем ниже, то мы видим,
что это происходит при вызове AssertEqual.
В чем тут дело?
Как раз в том, что мы передаем это значение и вот
этот нолик через разные типы, и компилятор понимает,
что тип T — это тип функции GetSynonymCount,
вот она у нас, это size_t, это беззнаковый тип.
А нолик, который мы там передаем,
вот этот вот, он, как мы с вами уже знаем, имеет тип int,
это тип всех числовых констант в C++ по умолчанию.
Поэтому у нас получается сравнение size_t с int, и компилятор ругается.
Как нам этого избежать, мы уже знаем.
Мы здесь просто напишем u и сделаем тем самым константы беззнаковыми.
Снова скомпилируем наш код.
Отлично, он компилируется.
Теперь мы поступим следующим образом.
У нас с вами в этом решении допущен баг,
который мы с вами уже исправляли несколько видео назад.
Мы его исправим еще раз, чтобы не стрелял тест на функцию AddSynonyms.
Выполним наш код.
Отлично, он выполнился.
Мы видим, что все юнит-тесты успешно отработали.
Прекрасно.
Но мы на самом деле ведь вот этот AssertEqual писали не на случай,
когда все тесты успешно работают, а когда тесты стреляют.
Давайте мы с вами осознанно допустим ошибку в GetSynonymCount и убедимся,
что AssertEqual действительно выводит в консоль аргументы, когда он срабатывает.
Запустим наш код, вот у нас явно выстрелил какой-то тест.
Смотрим в консоль, и мы видим сообщение Assertion failed: 1 != 0.
При этом вы видите,
что у нас пропала та удобная вещь, которая была в оригинальной функции Assert.
Мы не видим, какой именно assert сработал.
Мы сейчас эту проблему решим достаточно быстро.
Пока же мы видим, что мы действительно выводим в консоль значения аргументов,
которые были переданы в функцию AssertEqual.
Вот здесь мы осознанно
прибавили к результату 1, поэтому у нас появилась 1, хотя мы ожидали 0.
Хорошо.
Давайте вернем в AssertEqual то преимущество, которое было
в функции Assert, пусть она нам тоже будет говорить, какой именно assert сработал.
Поступим мы здесь таким образом.
Мы в AssertEqual будем передавать строчку
hint.
Эта строчка будет выводиться в конце сообщения
теста.
Hint: "<<hint.
Чтобы в экран влезало, я это отформатирую.
Тогда мы идем в функцию
TestCount и вот здесь
вот передаем уникальную строчку, которая нам позволит
однозначно идентифицировать тот assert, который сработал.
Допустим, здесь мы напишем count for
empty и здесь тоже укажем
какие-то уникальные строчки.
[БЕЗ_ЗВУКА] Компилируем то,
что у нас получилось.
Запускаем, видим, как у нас сработал assert.
Мы видим, что он сработал и вывел в консоль count for empty.
Теперь мы можем взять эту строчку и поискать
ее в исходниках.
И понять, какой именно assert у нас сработал.
Конечно, это не настолько удобно, как было в оригинальном Asssert.
Там не надо было ничего в него добавлять, чтобы он нам сказал,
в какой именно строчке сработала проверка.
На самом деле, нам на данный момент не хватает знаний C++,
чтобы повторить эту функциональность.
Поэтому мы воспользуемся теми знаниями, которые у нас уже есть, и вот таким,
пусть не самым элегантным и не самым удобным образом,
но все-таки мы решим проблему и научим наши assert'ы сообщать,
в каком именно месте сработала проверка.
Прекрасно.
Мы в этом видео смогли — давайте я сейчас его открою — написать
шаблонную функцию AssertEqual, которая позволяет увидеть в консоли
значения аргументов при срабатывании соответствующей проверки.
В следующих видео мы внедрим этот шаблон во все наши тесты,
которые есть в нашей программе.