Я не уверен, что согласен с «иметь» в утверждении «Удаление возможности комментировать из языка программирования означало, что я ДОЛЖЕН писать грамотный код, без исключений», поскольку это не так, как если бы весь код был задокументирован. Я предполагаю, что большинство людей будут писать нечитаемый код.
Более того, я лично не верю в реальность самоочевидной программы или API в практическом мире.
Мой опыт ручного анализа документации целых API для моей диссертации показывает, что слишком часто вам придется нести больше информации, чем вы могли бы передать только в подписи. Если вы исключите комментарии интерфейса из вашего языка, какие есть альтернативы? Нет документации не вариант. Внешняя документация с меньшей вероятностью будет прочитана.
Что касается внутренней документации, я вижу, что вы хотите сократить объем документации, чтобы убедить людей писать лучше. Тем не менее, комментарии служат многим целям сотрудничества и координации и предназначены для повышения осведомленности о вещах. Изгнав эти детали в внешние местоположения, вы уменьшаете вероятность того, что они придут к пониманию будущего читателя, если только вы не обладаете хорошими инструментами.
TDD - сначала напишите тесты, заставляет подумать о проверяемости и помогает написать код, который на самом деле необходимо, а не то, что вы думаете нужно
Рефакторинг интерфейсов - делает имитировать проще
Публичные методы виртуальны, если не используются интерфейсы - упрощает имитирование.
Внедрение зависимостей - делает насмешку проще
Меньшие, более целевые методы - тесты более сфокусированы, их легче пишите
Избегайте статических классов
Избегайте одиночных экземпляров, кроме случаев, когда необходимый
Избегайте запечатанных классов
Я постоянно пытаюсь найти процесс, в котором модульное тестирование менее утомительно и что я действительно ХОЧУ бы делать . По моему опыту, очень важным фактором являются ваши инструменты. Я много работаю с ActionScript, и, к сожалению, инструменты несколько ограничены, например, отсутствует интеграция с IDE и отсутствуют более продвинутые фреймворки для имитации (но хорошие вещи еще впереди, так что здесь никаких жалоб!). Раньше я занимался разработкой на основе тестов с более зрелыми фреймворками для тестирования, и это, безусловно, было более приятным занятием, но все же казалось несколько утомительным.
Однако недавно я начал писать код другим способом. Раньше я начинал с написания теста, наблюдения за их ошибками, написания кода для успешного выполнения теста, промывки и повторения и всего такого.
Теперь же я начинаю с написания интерфейсов, почти независимо от того, что я собираюсь делать . Сначала я, конечно, пытаюсь определить проблему и придумать решение. Затем я начинаю писать интерфейсы, чтобы получить некое абстрактное представление о коде и коммуникации. В этот момент я обычно понимаю, что я вообще не нашел правильного решения проблемы из-за того, что не полностью понимал проблему. Поэтому я возвращаюсь, пересматриваю решение и проверяю свои интерфейсы. Когда я чувствую, что интерфейсы отражают мое решение, я фактически начинаю с написания реализации, а не тестов. Когда у меня что-то реализовано (черновик реализации, обычно маленькие шаги), я начинаю это тестировать. Я продолжаю возвращаться между тестированием и внедрением, на несколько шагов вперед за раз. Поскольку у меня есть интерфейсы для всего, внедрять mock-объекты невероятно легко.
Я считаю, что такая работа, когда классы имеют очень мало знаний о других реализациях и общаются только с интерфейсами, чрезвычайно освобождает. Это освобождает меня от размышлений о реализации другого класса, и я могу сосредоточиться на текущем модуле. Все, что мне нужно знать, это контракт, который предоставляет интерфейс.
Но да, я все еще пытаюсь разработать процесс, который каждый раз работает супер-фантастически-потрясающе-хорошо.
О, я также хотел добавлю, что я не пишу тесты на все. Свойства ванили, которые не действуют Я много делаю, но переменные get / set бесполезны для тестирования. Языковой контракт гарантирует им работу. Если их нет, у меня будут проблемы похуже, чем мои устройства, не подлежащие тестированию.
Прочтите этот доклад Автоматизированные тестовые шаблоны и запахи . Одним из основных моментов для меня было убедиться, что код UnitTest находится в высоком качестве. Если код хорошо документирован и хорошо написан, каждый будет мотивирован продолжать в том же духе.
Я использую разработку через тестирование, когда это возможно, поэтому у меня нет какого-либо кода, который нельзя было бы протестировать модулем. Его не существовало бы, если бы сначала не существовал модульный тест.
I'm sure I'll be down voted for this, but I'm going to voice the opinion anyway :)
While many of the suggestions here have been good, I think it needs to be tempered a bit. The goal is to write more robust software that is changeable and maintainable.
The goal is not to have code that is unit testable. There's a lot of effort put into making code more "testable" despite the fact that testable code is not the goal. It sounds really nice and I'm sure it gives people the warm fuzzies, but the truth is all of those techniques, frameworks, tests, etc, come at a cost.
They cost time in training, maintenance, productivity overhead, etc. Sometimes it's worth it, sometimes it isn't, but you should never put the blinders on and charge ahead with making your code more "testable".
Не использовать git-log для написания сценариев: используйте либо git-rev-list
, либо git-log
с указанным настраиваемым форматом ( - format = *
option).
Есть дополнительная проблема с вашим вопросом: может существовать более одного таких корневых коммитов TAIL (без родителей) в репозитории (даже если мы не учитываем отключенные ветки, такие как 'html', 'man' и 'todo' в репозитории git.git). Обычно это результат объединения отдельных проектов в один или объединения поддеревьев отдельно разработанного подпроекта.
Например, в репозитории git есть 6 корневых коммитов: git-gui, gitk (объединено поддеревьев), gitweb (объединено, больше не разрабатывается отдельно), почтовые инструменты git (объединены очень рано в истории проекта) и p4-fast. -экспорт (возможно, случайно).
Небольшие, высокосвязные методы. Я узнал это на собственном горьком опыте. Представьте, что у вас есть общедоступный метод, который обрабатывает аутентификацию. Возможно, вы сделали TDD, но если метод большой, отладить будет сложно. Вместо этого, если этот метод #authenticate выполняет работу более псевдокодовым способом, вызывая другие небольшие методы (возможно, защищенные), когда обнаруживается ошибка, легко написать новые тесты для этих небольших методов и найти неисправный.
И кое-что, что вы узнаете в первую очередь в ООП, но многие, кажется, забывают: Код против интерфейсов , Не реализации .
Самый простой способ - не проверять свой код, если вы не проверяете с ним тесты.
Я не большой любитель сначала писать тесты. Но я очень сильно верю в то, что код в нужно проверять с помощью тестов. Ни даже часом раньше, вместе . Я думаю, что порядок, в котором они написаны, менее важен, если они идут вместе.
When writing tests (as with any other software task) Don't Repeat Yourself (DRY principle). If you have test data that is useful for more then one test then put it someplace where both tests can use it. Don't copy the code into both tests. I know this seems obvious but I see it happen all the time.
Убедитесь, что все ваши классы соблюдают Принцип единой ответственности . Единая ответственность означает, что у каждого класса должна быть одна и только одна ответственность. Это значительно упрощает модульное тестирование.
Сначала напишите тесты - так тесты будут определять ваш дизайн.
Потратьте некоторое время на рефакторинг непроверяемого кода, чтобы сделать его тестируемым. Напишите тесты и получите 95% покрытие. Это научило меня всему, что мне нужно знать о написании тестируемого кода. Я не против TDD, но изучение специфики того, что делает код тестируемым или нетестируемым, помогает вам думать о тестируемости во время разработки.
Вам не обязательно «делать ваш код более дружественным к модульному тестированию»
Вместо этого можно использовать набор инструментов для имитации, чтобы избавиться от проблем с тестируемостью. Одним из таких инструментов является JMockit .
Это похоже на простую проблему потребителя / производителя. Я бы использовал очередь с пулом потребителей. Вероятно, вы могли бы написать это с помощью нескольких строк кода, используя java.util.concurrent.
Это похоже на простую проблему потребителя / производителя. . Я бы использовал очередь с пулом потребителей. Вероятно, вы могли бы написать это с помощью нескольких строк кода, используя java.util.concurrent.