Изменить коммит
У git есть команда по изменению последнего локального коммита:
Но есть еще один случай использования. Бывает, что в процессе решения задачи в коде скапливается много “мусора” в виде избыточного логирования, лишних переменных, неоптимальных решений и т.п. Когда задача наконец-то решена, от этого мусора надо избавиться. И опыт показывает, что во время такой чистки есть риск что-то сломать. Да так сломать, что замучаешься восстанавливать. Поэтому хорошо бы иметь возможность откатиться назад.
Тут как раз поможет
У git есть команда по изменению последнего локального коммита:
git commit --ammend. Команда оказывается полезной, когда нужно исправить опечатку в сообщении коммита или добавить пропущенные файлы.Но есть еще один случай использования. Бывает, что в процессе решения задачи в коде скапливается много “мусора” в виде избыточного логирования, лишних переменных, неоптимальных решений и т.п. Когда задача наконец-то решена, от этого мусора надо избавиться. И опыт показывает, что во время такой чистки есть риск что-то сломать. Да так сломать, что замучаешься восстанавливать. Поэтому хорошо бы иметь возможность откатиться назад.
Тут как раз поможет
commit --ammend. Лучше сделать коммит как есть, со всем мусором, и только после этого чистить код. Все исправления будут видны в git diff и в случае проблем можно будет сделать шаг назад. Когда все вычищено и проверено, просто дополняем последний коммит новыми правками.👍2👌1
Условное логирование
В исходных кодах quagga применяется интересное решение отладочного логирования. Помимо привычного уже уровня логирования debugging, пользователь может включить дополнительный отладочный вывод отдельных сущностей. Например, очереди событий. Делается это добавлением строки вида
В коде этот подход реализуется простыми условным конструкциями вроде такой:
Занимательно, что quagga по умолчанию включает именно отладочный (читай “многословный”) уровень логирования. Хотя количество записей в логах сильно не вырастает. Большая часть вывода спрятана под условиями.
И что же получается… Код нашпигован условными конструкциями, которые не решают прикладную задачу, но выполняются при этом всегда. Я бы к такому решению никогда не пришёл - зачем нам лишние if-ы? В то же время мы видим сетевое приложение quagga, управляющее трафиком в реалтайме и совершенно не колебающееся из-за каких-то там if-ов.
Имеет место быть.
#ЖизньДругих
В исходных кодах quagga применяется интересное решение отладочного логирования. Помимо привычного уже уровня логирования debugging, пользователь может включить дополнительный отладочный вывод отдельных сущностей. Например, очереди событий. Делается это добавлением строки вида
“debug <сущность>” в файле конфигурации.В коде этот подход реализуется простыми условным конструкциями вроде такой:
if (IS_DEBUG_OSPF_EVENT)
zlog_debug ("setting options on %s accordingly", IF_NAME (oi));Занимательно, что quagga по умолчанию включает именно отладочный (читай “многословный”) уровень логирования. Хотя количество записей в логах сильно не вырастает. Большая часть вывода спрятана под условиями.
И что же получается… Код нашпигован условными конструкциями, которые не решают прикладную задачу, но выполняются при этом всегда. Я бы к такому решению никогда не пришёл - зачем нам лишние if-ы? В то же время мы видим сетевое приложение quagga, управляющее трафиком в реалтайме и совершенно не колебающееся из-за каких-то там if-ов.
Имеет место быть.
#ЖизньДругих
Логирование в Qt/C++
На фоне предыдущего поста поковырялся в инструментах логирования фреймворка Qt. Из коробки логгер Qt писать в файл не умеет, но поведение можно переопределить через
Как и log4cpp, Qt поддерживает категории логгера, для которых можно по-отдельности включать/отключать отладочный вывод через файл QtProject/qtlogging.ini.
Пример кода здесь.
На фоне предыдущего поста поковырялся в инструментах логирования фреймворка Qt. Из коробки логгер Qt писать в файл не умеет, но поведение можно переопределить через
qInstallMessageHandler(). Как и log4cpp, Qt поддерживает категории логгера, для которых можно по-отдельности включать/отключать отладочный вывод через файл QtProject/qtlogging.ini.
Пример кода здесь.
👍3
Шаблоны задач
Шаблоны задач - это хороший способ организации проекта. Существуют задачи с похожей структурой и соблюдение этой структуры важно для упрощения работы команды. Понятно, что все задачи под какой-то шаблон не подгонишь, но некоторые шаблонизировать все таки можно. Например, GitHub предлагает два типа шаблонов задач:
1. Баг (Bug). Собирает информацию о проблеме, ее воспроизведению и ожидаемому поведению.
2. Запрос фичи (Feature). Содержит предложение на реализацию новой функциональности.
Оба типа задач встречаются в любом проекте и имеют уже устоявшуюся структуру. В дополнение я бы выделил еще один тип задач, поддающийся шаблонизации:
3. Задача на знакомство с проектом (Onboarding).
Знакомство с проектом проходит одинаково для каждого нового разработчика: изучение документации и регламентов, знакомство с системой управления проектом, настройка рабочей среды, сборка и развертывание проекта и т.д. Подробный пошаговый список подзадач упростит подключение новичка к разработке и позволит руководителю контролировать этот процесс. После выполнения задачи новичок еще какое-то время будет использовать ее как справку, а руководитель при необходимости проведет коррекцию шаблона по результатам работы новичка.
Шаблоны задач - это хороший способ организации проекта. Существуют задачи с похожей структурой и соблюдение этой структуры важно для упрощения работы команды. Понятно, что все задачи под какой-то шаблон не подгонишь, но некоторые шаблонизировать все таки можно. Например, GitHub предлагает два типа шаблонов задач:
1. Баг (Bug). Собирает информацию о проблеме, ее воспроизведению и ожидаемому поведению.
2. Запрос фичи (Feature). Содержит предложение на реализацию новой функциональности.
Оба типа задач встречаются в любом проекте и имеют уже устоявшуюся структуру. В дополнение я бы выделил еще один тип задач, поддающийся шаблонизации:
3. Задача на знакомство с проектом (Onboarding).
Знакомство с проектом проходит одинаково для каждого нового разработчика: изучение документации и регламентов, знакомство с системой управления проектом, настройка рабочей среды, сборка и развертывание проекта и т.д. Подробный пошаговый список подзадач упростит подключение новичка к разработке и позволит руководителю контролировать этот процесс. После выполнения задачи новичок еще какое-то время будет использовать ее как справку, а руководитель при необходимости проведет коррекцию шаблона по результатам работы новичка.
👍4
Почему разработка ПО это сложно?
Не устаю размышлять на тему сложности разработки ПО. Ну почему для разработки и начала выпуска пассажирского авиалайнера требуется 5 лет, а разработка программ может вестись десятилетиями? Вопрос занятный и я объясняю его себе так:
1. Разработка ПО - это постоянное проектирование. Фаза конструирования по отношению к проектированию не велика, а сборку и вовсе выполняет компьютер за считанные минуты. Авиалайнер же за обозначенные 5 лет скорее конструируют, чем проектируют. Многие компоненты уже давно спроектированы.
2. Низкая стандартизация продукции и процессов. Грубо говоря, любая прихоть клиента должна быть исполнена, иначе он не купит продукт. “В вашем авиалайнере нет доступа из салона в багаж? Ну тогда поищу тех, у кого есть…” Бред? Конечно бред. Но в разработке ПО “пришить третий рукав” - это обычное дело. Стандарта то нет.
3. Высокие требования к отказоустойчивости. Если к управлению авиалайнером допускаются только профессионалы, прошедшие длительную подготовку, то использование прикладного ПО возможно кем угодно и как угодно. Программе необходимо выстоять при любом варианте использования, даже самом странном. Это все равно, что заставить авиалайнер нормально летать, даже если за штурвал сядет обезьяна.
4. Недостаточные компетенции разработчиков. Разработкой ПО могут заниматься специалисты с разным опытом. В то время как над авиалайнером работают сертифицированные инженеры. В ИТ сертификация специалистов пока только развивается.
Не устаю размышлять на тему сложности разработки ПО. Ну почему для разработки и начала выпуска пассажирского авиалайнера требуется 5 лет, а разработка программ может вестись десятилетиями? Вопрос занятный и я объясняю его себе так:
1. Разработка ПО - это постоянное проектирование. Фаза конструирования по отношению к проектированию не велика, а сборку и вовсе выполняет компьютер за считанные минуты. Авиалайнер же за обозначенные 5 лет скорее конструируют, чем проектируют. Многие компоненты уже давно спроектированы.
2. Низкая стандартизация продукции и процессов. Грубо говоря, любая прихоть клиента должна быть исполнена, иначе он не купит продукт. “В вашем авиалайнере нет доступа из салона в багаж? Ну тогда поищу тех, у кого есть…” Бред? Конечно бред. Но в разработке ПО “пришить третий рукав” - это обычное дело. Стандарта то нет.
3. Высокие требования к отказоустойчивости. Если к управлению авиалайнером допускаются только профессионалы, прошедшие длительную подготовку, то использование прикладного ПО возможно кем угодно и как угодно. Программе необходимо выстоять при любом варианте использования, даже самом странном. Это все равно, что заставить авиалайнер нормально летать, даже если за штурвал сядет обезьяна.
4. Недостаточные компетенции разработчиков. Разработкой ПО могут заниматься специалисты с разным опытом. В то время как над авиалайнером работают сертифицированные инженеры. В ИТ сертификация специалистов пока только развивается.
👍4❤1
Пример работы с QtTest
Составил простейшую инструкцию по созданию юнит-тестов на QtTest в QtCreator.
Теперь есть с чего начать.
Ссылки на официальную документацию присутствуют.
Составил простейшую инструкцию по созданию юнит-тестов на QtTest в QtCreator.
Теперь есть с чего начать.
Ссылки на официальную документацию присутствуют.
🙏1
Преобразование size_t в int
Тема преобразования типов в C++ довольно обширная. В этот раз в статье затронули преобразование size_t в int. Проблема тут может быть одна - это переполнение типа. И приводит она к двум ситуациям:
- большое значение size_t преобразуется в некорректное маленькое значение int;
- большое значение size_t преобразуется в отрицательное значение int.
Причём первая ситуация гораздо сложнее. Программа с большой вероятностью продолжит выполнение и даже выдаст результат. Но результат окажется некорректный.
Для предупреждения проблем с преобразованием автор предлагает такое решение:
То есть в случае чего бросаем исключение. Это хорошая иллюстрация принципа crash early: если программа не может продолжать работать безопасно, то завершаем ее как можно скорее.
Хорошо бы, конечно, вообще не доводить до таких преобразований. Это не сложно, если не разбрасываться типами. Но бывает всякое и надо знать выход.
Тема преобразования типов в C++ довольно обширная. В этот раз в статье затронули преобразование size_t в int. Проблема тут может быть одна - это переполнение типа. И приводит она к двум ситуациям:
- большое значение size_t преобразуется в некорректное маленькое значение int;
- большое значение size_t преобразуется в отрицательное значение int.
Причём первая ситуация гораздо сложнее. Программа с большой вероятностью продолжит выполнение и даже выдаст результат. Но результат окажется некорректный.
Для предупреждения проблем с преобразованием автор предлагает такое решение:
inline int SafeSizeToInt(size_t sizeValue)
{
constexpr int kIntMax = (std::numeric_limits<int>::max)();
if (sizeValue > static_cast<size_t>(kIntMax))
{
throw std::overflow_error("size_t value is too big to fit into an int.");
}
return static_cast<int>(sizeValue);
}То есть в случае чего бросаем исключение. Это хорошая иллюстрация принципа crash early: если программа не может продолжать работать безопасно, то завершаем ее как можно скорее.
Хорошо бы, конечно, вообще не доводить до таких преобразований. Это не сложно, если не разбрасываться типами. Но бывает всякое и надо знать выход.
👍4
Алгоритм или псевдокод
Продолжаю интересоваться терминами, которые вызывают путаницу в массах. И совсем неожиданно оказалась неясной разница между алгоритмом и псевдокодом. Разбираемся (хотя, казалось бы, чего тут разбираться).
Алгоритм - это идея, представленная как конечная последовательность действий.
Псевдокод - это неформальный инструмент реализации алгоритма, вариант его текстового представления.
Под псевдокодом понимаем некий усредненный язык программирования без углубления в синтаксические детали. Как будто UML-диаграмма в тексте. Простой и быстрый способ передать идею. Известно, что формальное математическое описание может быть слишком сложным, а неформальное словесное - трудным для восприятия. Псевдокод выступает где-то между, обеспечивая как математическую структурированность, так и словесную доступность.
#Словарь
Продолжаю интересоваться терминами, которые вызывают путаницу в массах. И совсем неожиданно оказалась неясной разница между алгоритмом и псевдокодом. Разбираемся (хотя, казалось бы, чего тут разбираться).
Алгоритм - это идея, представленная как конечная последовательность действий.
Псевдокод - это неформальный инструмент реализации алгоритма, вариант его текстового представления.
Под псевдокодом понимаем некий усредненный язык программирования без углубления в синтаксические детали. Как будто UML-диаграмма в тексте. Простой и быстрый способ передать идею. Известно, что формальное математическое описание может быть слишком сложным, а неформальное словесное - трудным для восприятия. Псевдокод выступает где-то между, обеспечивая как математическую структурированность, так и словесную доступность.
#Словарь
👍2
Разделение системы на модули (1972)
Попалась занятная статья от 1972 года по разделению программных систем на модули. Больше 50 лет прошло, а база все та же.
Автор говорит, что при разделении на модули мы получим:
- сокращение времени разработки, так как разные группы программистов могут работать над разными модулями;
- гибкость производства - можем менять один модуль, не трогая другой;
- простоту понимания - возможность изучать каждый модуль по отдельности.
Критерий разделения на модули предложен такой:
1. Во-первых, в отдельный модуль выделяется каждый крупный участок алгоритма системы.
2. Во-вторых, модуль должен скрывать внутри себя какое-то конкретное проектное решение.
При построении иерархии модулей важно, чтобы модули низкого уровня сохраняли свою работоспособность изолированно от модулей высокого уровня. Иначе само понятие уровней теряет смысл.
В конце автор приходит к выводу, что при разделении на модули неправильно основываться на алгоритме системы. Гораздо важнее выявить список сложных проектных решений, а также решений, наиболее подверженных изменениям, и скрыть их в отдельных модулях.
David Parnas - On the Criteria To Be Used in Decomposing Systems into Modules
Попалась занятная статья от 1972 года по разделению программных систем на модули. Больше 50 лет прошло, а база все та же.
Автор говорит, что при разделении на модули мы получим:
- сокращение времени разработки, так как разные группы программистов могут работать над разными модулями;
- гибкость производства - можем менять один модуль, не трогая другой;
- простоту понимания - возможность изучать каждый модуль по отдельности.
Критерий разделения на модули предложен такой:
1. Во-первых, в отдельный модуль выделяется каждый крупный участок алгоритма системы.
2. Во-вторых, модуль должен скрывать внутри себя какое-то конкретное проектное решение.
При построении иерархии модулей важно, чтобы модули низкого уровня сохраняли свою работоспособность изолированно от модулей высокого уровня. Иначе само понятие уровней теряет смысл.
В конце автор приходит к выводу, что при разделении на модули неправильно основываться на алгоритме системы. Гораздо важнее выявить список сложных проектных решений, а также решений, наиболее подверженных изменениям, и скрыть их в отдельных модулях.
David Parnas - On the Criteria To Be Used in Decomposing Systems into Modules
👍3
Doc As Code и C++
Немного поразмышлял на тему организации документации в стиле Doc As Code для проектов на C++.
Doc As Code в связке с Doxygen / Markdown - это отличный способ организовать документацию проекта. Вся документация размещается в репозитории рядом с исходным кодом. Для небольших проектов этого более чем достаточно.
Кстати, Doxygen поддерживает Java, Python, PHP. Поэтому рассмотренный подход справедлив и для них.
Немного поразмышлял на тему организации документации в стиле Doc As Code для проектов на C++.
Doc As Code в связке с Doxygen / Markdown - это отличный способ организовать документацию проекта. Вся документация размещается в репозитории рядом с исходным кодом. Для небольших проектов этого более чем достаточно.
Кстати, Doxygen поддерживает Java, Python, PHP. Поэтому рассмотренный подход справедлив и для них.
👍2🔥1
“Миры” Анатолия Сагалевича
Анатолий Михайлович Сагалевич - российский учёный, один из основных создателей глубоководных аппаратов “Мир-1” и “Мир-2” - знаменитых “шеститысячников”.
История учёного и история “Миров” удивляет и вдохновляет. Анатолия Сагалевича называют “подводным Гагариным”. Он провел тысячи часов под водой. Поистине уникальный опыт.
Свою известность “Миры” получили во многом благодаря фильму “Титаник” Джеймса Кэмерона. Все подводные съемки на месте крушения проводились на “Мирах”, а съемки пожилой Розы - на борту судна “Академик Мстислав Келдыш”, носителе “Миров”. Оборудованные манипуляторами, аппараты позволяли не только вести съемку, но и выполнять глубинные работы, поднимать со дна предметы.
На некоторых кадрах фильма можно разглядеть и Анатолия. Он играет самого себя.
Но по большей части “Мирами” решались научные и спасательные задачи: геология океанского дна, исследования затонувших судов, консервирование АПЛ “Комсомолец”, подготовка к подъему подлодки “Курск”, достижение Северного полюса Земли (под водой впервые в истории) и многие другие.
И тем не менее судьбу проекта “Мир” решили в кабинетах. Из-за дороговизны проект был закрыт, а эксплуатация "Миров" прекращена после более чем 20 лет работы. Все попытки Сагалевича возобновить работу на “Мирах” не имели успеха. После закрытия проекта Анатолий Михайлович продолжил трудиться в области океанологии.
Работа учёного никогда не заканчивается. Наука - это поиск.
А.М, Сагалевич - "Глубина"
#КнижнаяПолка
Анатолий Михайлович Сагалевич - российский учёный, один из основных создателей глубоководных аппаратов “Мир-1” и “Мир-2” - знаменитых “шеститысячников”.
История учёного и история “Миров” удивляет и вдохновляет. Анатолия Сагалевича называют “подводным Гагариным”. Он провел тысячи часов под водой. Поистине уникальный опыт.
Свою известность “Миры” получили во многом благодаря фильму “Титаник” Джеймса Кэмерона. Все подводные съемки на месте крушения проводились на “Мирах”, а съемки пожилой Розы - на борту судна “Академик Мстислав Келдыш”, носителе “Миров”. Оборудованные манипуляторами, аппараты позволяли не только вести съемку, но и выполнять глубинные работы, поднимать со дна предметы.
На некоторых кадрах фильма можно разглядеть и Анатолия. Он играет самого себя.
Но по большей части “Мирами” решались научные и спасательные задачи: геология океанского дна, исследования затонувших судов, консервирование АПЛ “Комсомолец”, подготовка к подъему подлодки “Курск”, достижение Северного полюса Земли (под водой впервые в истории) и многие другие.
И тем не менее судьбу проекта “Мир” решили в кабинетах. Из-за дороговизны проект был закрыт, а эксплуатация "Миров" прекращена после более чем 20 лет работы. Все попытки Сагалевича возобновить работу на “Мирах” не имели успеха. После закрытия проекта Анатолий Михайлович продолжил трудиться в области океанологии.
Работа учёного никогда не заканчивается. Наука - это поиск.
А.М, Сагалевич - "Глубина"
#КнижнаяПолка
🔥3
Какой из вас оценщик?
Стив Макконнелл пишет: “Разработчикам программного обеспечения часто приходится оценивать проекты из незнакомых областей - проекты, в реализации которых задействованы новые технологии, новые средства программирования, незнакомый персонал и т.д. Оценка в условиях неопределенности является вполне обычным делом”.
И он же дает простой тест по оценке. Рекомендую попробовать свои силы.
По каждому вопросу нужно записать нижнюю и верхнюю границу, которые, на ваш взгляд, включают правильное значение. Правильные ответы для проверки найдете в комментариях.
1. Температура поверхности солнца?
2. Широта Шанхая?
3. Площадь континента Азия?
4. Год рождения Александра Македонского?
5. Общая стоимость американской валюты, находившейся в обращении в 2004г?
6. Общий объем Великих Озер?
7. Мировые кассовые сборы фильма “Титаник”?
8. Общая длина линии побережья Тихого океана?
9. Количество названий книг, опубликованных в США с 1776 года?
10. Максимальный зафиксированный вес голубого кита?
Мои оценки попали в правильный ответ только в 3-х вопросах из 10 😁
Я - большинство. В основном люди отвечают правильно от 1 до 3 вопросов.
Пишите, что у вас получилось.
Макконнелл С. - “Сколько стоит программный проект”
Стив Макконнелл пишет: “Разработчикам программного обеспечения часто приходится оценивать проекты из незнакомых областей - проекты, в реализации которых задействованы новые технологии, новые средства программирования, незнакомый персонал и т.д. Оценка в условиях неопределенности является вполне обычным делом”.
И он же дает простой тест по оценке. Рекомендую попробовать свои силы.
По каждому вопросу нужно записать нижнюю и верхнюю границу, которые, на ваш взгляд, включают правильное значение. Правильные ответы для проверки найдете в комментариях.
1. Температура поверхности солнца?
2. Широта Шанхая?
3. Площадь континента Азия?
4. Год рождения Александра Македонского?
5. Общая стоимость американской валюты, находившейся в обращении в 2004г?
6. Общий объем Великих Озер?
7. Мировые кассовые сборы фильма “Титаник”?
8. Общая длина линии побережья Тихого океана?
9. Количество названий книг, опубликованных в США с 1776 года?
10. Максимальный зафиксированный вес голубого кита?
Мои оценки попали в правильный ответ только в 3-х вопросах из 10 😁
Я - большинство. В основном люди отвечают правильно от 1 до 3 вопросов.
Пишите, что у вас получилось.
Макконнелл С. - “Сколько стоит программный проект”
👍3
DrMemory: поиск утечек памяти
DrMemory - это простой инструмент для определения утечек памяти в программе. Интересная альтернатива Valgrind на Windows. Попробовал на C++ проектах, работает.
Запускается через интерфейс командной строки:
На выходе получаем текстовый файл results.txt, в котором перечислены обнаруженные проблемы, в том числе и утечки памяти. Каждая утечка памяти обозначается отдельным пунктом с меткой “LEAK”, включающим количество потерянных байт и стек вызовов, по которому можно найти оператор выделения памяти. Например:
DrMemory - это простой инструмент для определения утечек памяти в программе. Интересная альтернатива Valgrind на Windows. Попробовал на C++ проектах, работает.
Запускается через интерфейс командной строки:
drmemory.exe -- c:/path/to/my/app args to my app
На выходе получаем текстовый файл results.txt, в котором перечислены обнаруженные проблемы, в том числе и утечки памяти. Каждая утечка памяти обозначается отдельным пунктом с меткой “LEAK”, включающим количество потерянных байт и стек вызовов, по которому можно найти оператор выделения памяти. Например:
Error #9: LEAK 32 direct bytes 0x0000024580be88a0-0x0000024580be88c0 + 556 indirect bytes
# 0 replace_operator_new [D:\a\drmemory\drmemory\common\alloc_replace.c:2903]
# 1 MockFuse::BuildImpl [D:\git\temp\Mocks.h:127]
# 2 main [D:\git\temp\main.cpp:3]
👍3
Профилирование C++ кода в Visual Studio без инструментирования
В новой инструкции рассмотрел возможности профилировщика, встроенного в Visual Studio. Профилировщик Visual Studio может работать без инструментирования целевой программы, измеряя только время центрального процессора. Этот простой и быстрый способ в большинстве случаев позволяет обнаружить проблемы с производительностью программы.
В новой инструкции рассмотрел возможности профилировщика, встроенного в Visual Studio. Профилировщик Visual Studio может работать без инструментирования целевой программы, измеряя только время центрального процессора. Этот простой и быстрый способ в большинстве случаев позволяет обнаружить проблемы с производительностью программы.
👍2
Где инклудить заголовочники в C++?
Короткий ответ: инклудим только то, что нужно и только там, где нужно. Стараемся избегать лишних зависимостей.
Для большей ясности добавлю пару популярных замечаний.
Во-первых, не нужно собирать все инклуды в заголовочном файле класса. Наоборот, максимально переносим их в cpp-файл.
Во-вторых, нужно максимально использовать предварительное объявление (forward declaration) в заголовочных файлах. Часто в заголовочнике достаточно указать только имя класса, а инклуд перенести в cpp-файл. Такое бывает, когда класс используется исключительно в определениях методов, либо хранится внутри класса по ссылке или указателю.
Например, делаем так в
И потом так в
Правильное размещение инклудов значительно облегчает чтение кода и может сократить время сборки проекта.
См. еще про предварительное объявление в правиле 22 у Саттера.
Короткий ответ: инклудим только то, что нужно и только там, где нужно. Стараемся избегать лишних зависимостей.
Для большей ясности добавлю пару популярных замечаний.
Во-первых, не нужно собирать все инклуды в заголовочном файле класса. Наоборот, максимально переносим их в cpp-файл.
Во-вторых, нужно максимально использовать предварительное объявление (forward declaration) в заголовочных файлах. Часто в заголовочнике достаточно указать только имя класса, а инклуд перенести в cpp-файл. Такое бывает, когда класс используется исключительно в определениях методов, либо хранится внутри класса по ссылке или указателю.
Например, делаем так в
MyWindow.h:class MyClass; // <----- Forward declaration
class MyWindow
{
MyWindow( MyClass* var );
MyClass* var_;
};
И потом так в
MyWindow.cpp:#include "MyWindow.h"
#include "MyClass.h" // <-----
MyWindow::MyWindow( MyClass* var ): var_( var ) {}
Правильное размещение инклудов значительно облегчает чтение кода и может сократить время сборки проекта.
См. еще про предварительное объявление в правиле 22 у Саттера.
👍1🙏1
Гифки в ScreenToGif
ScreenToGif умеет записывать видеоряд с экрана, редактировать его и сохранять в gif или видео. Без звука, только картинка. Написан на C#, опенсорс.
Как бы это не было странно, но инструмент по созданию gif-ок оказался полезен и в разработке.
С помощью ScreenToGif решаю такие задачи:
1. Визуализация воспроизведения бага для баг-трекера или отчета. У ScreenToGif записанный видеоряд представляется в виде последовательности скриншотов. Поверх скриншотов можно что-то нарисовать: стрелки, подписи, рамки и т.п. Очень подходит для вставки дополнительных пояснений при воспроизведении бага.
2. Запись происходящего на экране в целях отладки. Не все программы пишут свои логи в файлы. Некоторые выводят свои сообщения только на экран. Да ещё и так быстро, что невозможно успеть что-то разобрать. Иногда и проскроллить обратно нельзя. Поэтому покадровый просмотр записи экрана оказывается полезным. К тому же некоторые скриншоты потом тоже использую в отчетах.
ScreenToGif умеет записывать видеоряд с экрана, редактировать его и сохранять в gif или видео. Без звука, только картинка. Написан на C#, опенсорс.
Как бы это не было странно, но инструмент по созданию gif-ок оказался полезен и в разработке.
С помощью ScreenToGif решаю такие задачи:
1. Визуализация воспроизведения бага для баг-трекера или отчета. У ScreenToGif записанный видеоряд представляется в виде последовательности скриншотов. Поверх скриншотов можно что-то нарисовать: стрелки, подписи, рамки и т.п. Очень подходит для вставки дополнительных пояснений при воспроизведении бага.
2. Запись происходящего на экране в целях отладки. Не все программы пишут свои логи в файлы. Некоторые выводят свои сообщения только на экран. Да ещё и так быстро, что невозможно успеть что-то разобрать. Иногда и проскроллить обратно нельзя. Поэтому покадровый просмотр записи экрана оказывается полезным. К тому же некоторые скриншоты потом тоже использую в отчетах.
👍1
Поверхностный багфикс
Есть такое понятие - “поверхностная медицина”. Это когда врач цепляется за первую попавшуюся болячку или нестыковку, которой объясняет проблему пациента. При этом другие возможные причины болячки не проверяет.
Был пациент с микроинсультом. Пациента обследовали, сняли КТ, и кардиолог обнаружил незакрытое овальное окошко в сердце. Доктор тут же обозначил это как причину инсульта и назначил операцию по закрытию окошка. Пациент же на всякий случай сходил к другому кардиологу, который решил проверить другие варианты возникновения инсультов и повесил на пациента холтер на 12 часов.
В итоге была обнаружена аритмия, проявляющаяся в течение дня и особенно во сне. А именно аритмии с гораздо большей вероятностью приводят к инсульту, чем дефекты анатомии сердца. Обычное медикаментозное лечение позволило устранить проблему без операционного вмешательства.
Аналогичные вещи происходят и в поиске источника бага в программе. Программист спешит устранить симптом, который лежит на поверхности, не доходя до истинного источника проблемы. Таким образом проблема продолжает неявно существовать до своего следующего проявления.
Про поверхностную медицину см. здесь: Эрик Тополь - Искусственный интеллект в медицине. Как умные технологии меняют подход к лечению.
Есть такое понятие - “поверхностная медицина”. Это когда врач цепляется за первую попавшуюся болячку или нестыковку, которой объясняет проблему пациента. При этом другие возможные причины болячки не проверяет.
Был пациент с микроинсультом. Пациента обследовали, сняли КТ, и кардиолог обнаружил незакрытое овальное окошко в сердце. Доктор тут же обозначил это как причину инсульта и назначил операцию по закрытию окошка. Пациент же на всякий случай сходил к другому кардиологу, который решил проверить другие варианты возникновения инсультов и повесил на пациента холтер на 12 часов.
В итоге была обнаружена аритмия, проявляющаяся в течение дня и особенно во сне. А именно аритмии с гораздо большей вероятностью приводят к инсульту, чем дефекты анатомии сердца. Обычное медикаментозное лечение позволило устранить проблему без операционного вмешательства.
Аналогичные вещи происходят и в поиске источника бага в программе. Программист спешит устранить симптом, который лежит на поверхности, не доходя до истинного источника проблемы. Таким образом проблема продолжает неявно существовать до своего следующего проявления.
Про поверхностную медицину см. здесь: Эрик Тополь - Искусственный интеллект в медицине. Как умные технологии меняют подход к лечению.
🔥5👍1
Донни Браско
Джозеф Пистоне, он же Донни Браско, - агент ФБР по внедрению. Известен тем, что шесть лет проработал под прикрытием, внедряясь в нью-йоркскую мафию. Никто до него не проводил такую длительную операцию и не внедрялся так глубоко.
Все невероятно интересно в его истории, рекомендую познакомиться. И книги есть, и кино. Я же выделю главный для себя момент…
Раньше я писал здесь об известных учёных: Дайан Фосси, Анатолий Сагалевич. Они в каком-то смысле пионеры в своей области, первопроходцы. И точно так же Донни пионер в своей.
Все трое сталкивались с новыми вызовами: никто такого раньше не делал, такого опыта нет и некого спросить. Донни писал: “Самые тяжёлые решения надо принимать самостоятельно и с ходу… Мне, например, не приходилось рассчитывать на руководителей ФБР из Вашингтона”. Один на один со своей проблемой, никто не поможет.
Такие истории вдохновляют. Мы, программисты, нередко оказываемся в похожей ситуации. Особенно в инновационных проектах, где степень повторяемости задач низкая. В этом бесконечном пространстве вопросов и ответов нам нужно найти правильные. Правильные вопросы и правильные ответы. Невозможно сказать: “Я не знаю”. В любом случае что-то мы должны сделать: пусть не точное или где-то ошибочное. Потом от этого мы сможем оттолкнуться. И если не мы сами, так новые умы.
#КнижнаяПолка
Джозеф Пистоне, он же Донни Браско, - агент ФБР по внедрению. Известен тем, что шесть лет проработал под прикрытием, внедряясь в нью-йоркскую мафию. Никто до него не проводил такую длительную операцию и не внедрялся так глубоко.
Все невероятно интересно в его истории, рекомендую познакомиться. И книги есть, и кино. Я же выделю главный для себя момент…
Раньше я писал здесь об известных учёных: Дайан Фосси, Анатолий Сагалевич. Они в каком-то смысле пионеры в своей области, первопроходцы. И точно так же Донни пионер в своей.
Все трое сталкивались с новыми вызовами: никто такого раньше не делал, такого опыта нет и некого спросить. Донни писал: “Самые тяжёлые решения надо принимать самостоятельно и с ходу… Мне, например, не приходилось рассчитывать на руководителей ФБР из Вашингтона”. Один на один со своей проблемой, никто не поможет.
Такие истории вдохновляют. Мы, программисты, нередко оказываемся в похожей ситуации. Особенно в инновационных проектах, где степень повторяемости задач низкая. В этом бесконечном пространстве вопросов и ответов нам нужно найти правильные. Правильные вопросы и правильные ответы. Невозможно сказать: “Я не знаю”. В любом случае что-то мы должны сделать: пусть не точное или где-то ошибочное. Потом от этого мы сможем оттолкнуться. И если не мы сами, так новые умы.
#КнижнаяПолка
👍3👌1
Запуск DrMemory из QtCreator
Продолжая тему анализатора утечек памяти DrMemory, сделал инструкцию по запуску DrMemory из QtCreator.
Полезно раскладывать нужные инструменты под рукой. Как минимум не так лениво будет ими воспользоваться.
Продолжая тему анализатора утечек памяти DrMemory, сделал инструкцию по запуску DrMemory из QtCreator.
Полезно раскладывать нужные инструменты под рукой. Как минимум не так лениво будет ими воспользоваться.
🙏1
Выбор вещественного типа C++
В C++ есть два типа вещественных чисел:
- Используем
- Используем
- Есть ещё
When do you use float and when do you use double
В C++ есть два типа вещественных чисел:
float и double. Отсюда часто задают вопрос, какой и когда использовать. Проще всего так:- Используем
double по умолчанию. Всегда.- Используем
float, если приходится работать с огромными массивами (порядка 10⁶ и более), где double займёт непозволительно много памяти. Но нужно учесть риски снижения точности float по отношению к double.- Есть ещё
long double, который нужно использовать, если не хватило точности double. В своей практике я с таким не сталкивался.When do you use float and when do you use double
👍2
Тайм-менеджмент и кандидатская диссертация
Нашел старый документ, где я пытался управлять своим временем, когда готовил кандидатскую. Я вел обычный учет трудозатрат с небольшой статистикой в LibreOffice Calc (бесплатный Excel).
Выглядит занятно и в какой-то степени маниакально. Но такая своего рода геймификация процесса помогла тогда организоваться. Подробности в статье.
Нашел старый документ, где я пытался управлять своим временем, когда готовил кандидатскую. Я вел обычный учет трудозатрат с небольшой статистикой в LibreOffice Calc (бесплатный Excel).
Выглядит занятно и в какой-то степени маниакально. Но такая своего рода геймификация процесса помогла тогда организоваться. Подробности в статье.
🔥4👍2