SlideShare a Scribd company logo
1 of 49
Комплексное использование
анализаторов для повышения
качества кода
Юрий Минаев (PVS-Studio)
О себе
2
• Юрий Минаев
• C++ разработчик в
компании PVS-Studio
• minaev@viva64.com
О чем пойдет речь
• Об инструментах, помогающих обеспечить
качество кода
• О SonarQube как единой платформе контроля
качества
3
Зачем это нужно
• В любом проекте есть баги
• Исправлять их проще,
пока они не выросли
• Автоматизация – это
удобно
4
Стоимость исправления дефекта
5
Как защитить код от багов
6
Code review
7
Оформление кода
• Единообразный стиль
• Читаемость
• Облегчение отладки
• Проще найти дефекты
8
Оформление кода: пример
void DoSomething(Things& things, bool remove) {
for (auto i = 0; i < things.Count(); ++i) {
things[i].DoWhatever();
if (remove) {things.Remove(i);
} else { things.ApplyChange(i); } }
}
9
Оформление кода: пример
void DoSomething(Things& things, bool remove)
{
for (auto i = 0; i < things.Count(); ++i)
{
things[i].DoWhatever();
if (remove)
things.Remove(i);
else
things.ApplyChange(i);
}
}
10
Статический анализ
• Это как code review, только происходит
автоматически
• Хорошо сочетается с другими методами
• Находит ошибочные паттерны, о которых не
догадываются программисты
11
Code smells
• Дублирование кода
• Длинные функции
• Слишком много
параметров
• God object
12
Code smells: пример
class ManagerOfEverything
{
public:
void InitDatabase();
void UpdateDatabase();
int CalculateSomeImportantValue();
//…
void SendRequest(const RequestData& data);
void ReceiveRequest(RequestData& data);
//…
void CreateInputForm();
void FillInputForm(const FormData& data);
//…
void MakeMeACoffee();
};
13
Code smells != errors
• Даже если код пахнет, это не
значит, что он работает
неправильно
14
Code smells != errors, но...
• Такой код сложнее отлаживать
• Как правило, сложнее читать
• Сложнее найти баги
• Сложнее исправить баги
15
Динамический анализ
• Отладчики
• Профилировщики
• Санитайзеры
• В некоторой степени юнит-тесты
16
AddressSanitizer
17
#include <stdlib.h>
int main()
{
char* x = (char*)malloc(10 * sizeof(char*));
free(x);
return x[5];
}
AddressSanitizer
==9901==ERROR: AddressSanitizer: heap-use-after-free on address 0x60700000dfb5 at pc 0x45917b bp 0x7fff4490c700
sp 0x7fff4490c6f8
READ of size 1 at 0x60700000dfb5 thread T0
#0 0x45917a in main use-after-free.c:5
#1 0x7fce9f25e76c in __libc_start_main /build/buildd/eglibc-2.15/csu/libc-start.c:226
#2 0x459074 in _start (a.out+0x459074)
0x60700000dfb5 is located 5 bytes inside of 80-byte region [0x60700000dfb0,0x60700000e000)
freed by thread T0 here:
#0 0x4441ee in __interceptor_free projects/compiler-rt/lib/asan/asan_malloc_linux.cc:64
#1 0x45914a in main use-after-free.c:4
#2 0x7fce9f25e76c in __libc_start_main /build/buildd/eglibc-2.15/csu/libc-start.c:226
previously allocated by thread T0 here:
#0 0x44436e in __interceptor_malloc projects/compiler-rt/lib/asan/asan_malloc_linux.cc:74
#1 0x45913f in main use-after-free.c:3
#2 0x7fce9f25e76c in __libc_start_main /build/buildd/eglibc-2.15/csu/libc-start.c:226
SUMMARY: AddressSanitizer: heap-use-after-free use-after-free.c:5 main
18
Метрики
• Определение качества существующего
продукта
• Прогнозирование качества продукта
• Улучшение качества продукта
19
Количественные метрики
• Строки кода (SLOC)
• Количество и процент комментариев
• Среднее число строк на функцию/класс/файл
• Процент дублирования кода
• Цикломатическая сложность
20
Метрика по дефектам в коде
• Плотность дефектов в коде
• Number of Defects – общее количество дефектов
• Size – размер кодовой базы
21
• Платформа с открытым исходным кодом для
непрерывного анализа и измерения качества кода
• Содержит ряд анализаторов для разных языков
• Позволяет интегрировать сторонние анализаторы
• Наглядно визуализирует качество вашего продукта
22
Как это использовать
23
Что нам понадобится
• JRE 8
• SonarQube LTS
https://www.sonarqube.org/downloads/
• SonarQube C++ Community Plugin
https://github.com/SonarOpenCommunity/sonar-cxx
24
25
Подготовка
• Quality profile
• Quality gate
• Конфигурационный файл
26
Quality profile
27
Quality gate
28
sonar-project.properties
sonar.projectKey=demo
sonar.projectName=demo
sonar.projectVersion=1.0
sonar.projectBaseDir=SonarTest
sonar.sources=Thingy
sonar.host.url=http://localhost:9000
29
Первый запуск
30
Настройка правил
31
CppCheck
• Статический анализатор с открытым исходным
кодом
• Основан на регулярных выражениях
• Позволяет добавлять собственные правила
• http://cppcheck.sourceforge.net/
32
CppCheck
33
sonar.cxx.cppcheck.reportPath=../cppcheck.xml
Clang-Tidy
• Линтер для языков C и C++
• Позволяет проверять code style
• Позволяет добавлять собственные правила
• Поставляется вместе с LLVM
• https://clang.llvm.org/extra/clang-tidy/
34
Clang-Tidy
35
sonar.cxx.clangtidy.reportPath=../tidy.log
PVS-Studio
• Статический анализатор для C, C++, C# и Java
• Для подключения к SonarQube нужен
специальный плагин (идет в поставке)
• https://www.viva64.com/
36
PVS-Studio
37
sonar.pvs-studio.reportPath=report.plog
Valgrind
• Динамический анализатор с открытым
исходным кодом
• Работает под Linux
• http://www.valgrind.org/
38
Valgrind
39
sonar.cxx.valgrind.reportPath=../valgrind.xml
Оценка покрытия кода
• Имеет смысл запускать с юнит-тестами
• Позволяет оценить, насколько хорошо
покрыты разные пути выполнения
40
Gcov
• Утилита для оценки покрытия кода
• Часть GCC
• https://gcc.gnu.org/onlinedocs/gcc/Gcov-Intro.html
41
Gcov
42
sonar.cxx.coverage.reportPath=../gcov.xml
Результат
43
Результат
44
Результат
45
Результат
46
Результат
47
Итог
• Качество кода можно
обеспечить разными
инструментами
• Полезно использовать их в
комплексе
• "Серебряной пули" не бывает
48
Q&A
• Сайт PVS-Studio:
https://www.viva64.com
• Контакты:
Юрий Минаев
minaev@viva64.com
49

More Related Content

Similar to Комплексное использование анализаторов для повышения качества кода

Как не подавиться большим старым проектом. Юрий Минаев ➠ CoreHard Autumn 2019
Как не подавиться большим старым проектом. Юрий Минаев ➠  CoreHard Autumn 2019Как не подавиться большим старым проектом. Юрий Минаев ➠  CoreHard Autumn 2019
Как не подавиться большим старым проектом. Юрий Минаев ➠ CoreHard Autumn 2019corehard_by
 
Как не подавиться большим старым проектом
Как не подавиться большим старым проектомКак не подавиться большим старым проектом
Как не подавиться большим старым проектомAndrey Karpov
 
РИФ 2016, Внедрение контроля качества в большом web-проекте на примере Badoo
РИФ 2016, Внедрение контроля качества в большом web-проекте на примере BadooРИФ 2016, Внедрение контроля качества в большом web-проекте на примере Badoo
РИФ 2016, Внедрение контроля качества в большом web-проекте на примере BadooТарасов Константин
 
Статические анализаторы кода как DevSecOps решение
Статические анализаторы кода как DevSecOps решениеСтатические анализаторы кода как DevSecOps решение
Статические анализаторы кода как DevSecOps решениеAndrey Karpov
 
Юрий Василевский "Автоматизация в XCode"
Юрий Василевский "Автоматизация в XCode"Юрий Василевский "Автоматизация в XCode"
Юрий Василевский "Автоматизация в XCode"Yandex
 
Юрий Василевский «Автоматизация в XCode»
Юрий Василевский «Автоматизация в XCode»Юрий Василевский «Автоматизация в XCode»
Юрий Василевский «Автоматизация в XCode»Yandex
 
Модульное тестирование и TDD в .NET
Модульное тестирование и TDD в .NETМодульное тестирование и TDD в .NET
Модульное тестирование и TDD в .NETAlexander Byndyu
 
Continuous Integration для QA
Continuous Integration для QAContinuous Integration для QA
Continuous Integration для QAIvan Kolodyazhny
 
Современный статический анализ кода: что умеет он, чего не умели линтеры
Современный статический анализ кода: что умеет он, чего не умели линтерыСовременный статический анализ кода: что умеет он, чего не умели линтеры
Современный статический анализ кода: что умеет он, чего не умели линтерыcorehard_by
 
Software Analytics in frontend
Software Analytics in frontendSoftware Analytics in frontend
Software Analytics in frontendDenis Kolesnikov
 
Юлия Викторова; Александр Тарасов. DevOps без булшита.
Юлия Викторова; Александр Тарасов. DevOps без булшита.Юлия Викторова; Александр Тарасов. DevOps без булшита.
Юлия Викторова; Александр Тарасов. DevOps без булшита.ScrumTrek
 
Технический долг: взгляд и действия со стороны QA / QC&AT
Технический долг: взгляд и действия со стороны QA / QC&ATТехнический долг: взгляд и действия со стороны QA / QC&AT
Технический долг: взгляд и действия со стороны QA / QC&ATCodeFest
 
Основы и применение статического анализа кода при разработке лекция 1
Основы и применение статического анализа кода при разработке лекция 1Основы и применение статического анализа кода при разработке лекция 1
Основы и применение статического анализа кода при разработке лекция 1m2rus
 
Применение статического анализа кода в преподавании и в разработке свободного ПО
Применение статического анализа кода в преподавании и в разработке свободного ПОПрименение статического анализа кода в преподавании и в разработке свободного ПО
Применение статического анализа кода в преподавании и в разработке свободного ПОAndrey Karpov
 
Автоматическое тестирование. Моя система
Автоматическое тестирование. Моя системаАвтоматическое тестирование. Моя система
Автоматическое тестирование. Моя системаIgor Lyubin
 
Static code analysis of the projects built on Unreal Engine
Static code analysis of the projects built on Unreal EngineStatic code analysis of the projects built on Unreal Engine
Static code analysis of the projects built on Unreal EngineDevGAMM Conference
 
Статический анализ кода проектов, построенных на движке Unreal Engine
Статический анализ кода проектов, построенных на движке Unreal EngineСтатический анализ кода проектов, построенных на движке Unreal Engine
Статический анализ кода проектов, построенных на движке Unreal EngineAndrey Karpov
 
Лучшие практики на практике
Лучшие практики на практикеЛучшие практики на практике
Лучшие практики на практикеDenis Tuchin
 
Инструмент ChangelogBuilder для автоматической подготовки Release Notes
Инструмент ChangelogBuilder для автоматической подготовки Release NotesИнструмент ChangelogBuilder для автоматической подготовки Release Notes
Инструмент ChangelogBuilder для автоматической подготовки Release NotesPositive Hack Days
 
Jbreak 2016: Твой личный Spring Boot Starter
Jbreak 2016: Твой личный Spring Boot StarterJbreak 2016: Твой личный Spring Boot Starter
Jbreak 2016: Твой личный Spring Boot StarterAleksandr Tarasov
 

Similar to Комплексное использование анализаторов для повышения качества кода (20)

Как не подавиться большим старым проектом. Юрий Минаев ➠ CoreHard Autumn 2019
Как не подавиться большим старым проектом. Юрий Минаев ➠  CoreHard Autumn 2019Как не подавиться большим старым проектом. Юрий Минаев ➠  CoreHard Autumn 2019
Как не подавиться большим старым проектом. Юрий Минаев ➠ CoreHard Autumn 2019
 
Как не подавиться большим старым проектом
Как не подавиться большим старым проектомКак не подавиться большим старым проектом
Как не подавиться большим старым проектом
 
РИФ 2016, Внедрение контроля качества в большом web-проекте на примере Badoo
РИФ 2016, Внедрение контроля качества в большом web-проекте на примере BadooРИФ 2016, Внедрение контроля качества в большом web-проекте на примере Badoo
РИФ 2016, Внедрение контроля качества в большом web-проекте на примере Badoo
 
Статические анализаторы кода как DevSecOps решение
Статические анализаторы кода как DevSecOps решениеСтатические анализаторы кода как DevSecOps решение
Статические анализаторы кода как DevSecOps решение
 
Юрий Василевский "Автоматизация в XCode"
Юрий Василевский "Автоматизация в XCode"Юрий Василевский "Автоматизация в XCode"
Юрий Василевский "Автоматизация в XCode"
 
Юрий Василевский «Автоматизация в XCode»
Юрий Василевский «Автоматизация в XCode»Юрий Василевский «Автоматизация в XCode»
Юрий Василевский «Автоматизация в XCode»
 
Модульное тестирование и TDD в .NET
Модульное тестирование и TDD в .NETМодульное тестирование и TDD в .NET
Модульное тестирование и TDD в .NET
 
Continuous Integration для QA
Continuous Integration для QAContinuous Integration для QA
Continuous Integration для QA
 
Современный статический анализ кода: что умеет он, чего не умели линтеры
Современный статический анализ кода: что умеет он, чего не умели линтерыСовременный статический анализ кода: что умеет он, чего не умели линтеры
Современный статический анализ кода: что умеет он, чего не умели линтеры
 
Software Analytics in frontend
Software Analytics in frontendSoftware Analytics in frontend
Software Analytics in frontend
 
Юлия Викторова; Александр Тарасов. DevOps без булшита.
Юлия Викторова; Александр Тарасов. DevOps без булшита.Юлия Викторова; Александр Тарасов. DevOps без булшита.
Юлия Викторова; Александр Тарасов. DevOps без булшита.
 
Технический долг: взгляд и действия со стороны QA / QC&AT
Технический долг: взгляд и действия со стороны QA / QC&ATТехнический долг: взгляд и действия со стороны QA / QC&AT
Технический долг: взгляд и действия со стороны QA / QC&AT
 
Основы и применение статического анализа кода при разработке лекция 1
Основы и применение статического анализа кода при разработке лекция 1Основы и применение статического анализа кода при разработке лекция 1
Основы и применение статического анализа кода при разработке лекция 1
 
Применение статического анализа кода в преподавании и в разработке свободного ПО
Применение статического анализа кода в преподавании и в разработке свободного ПОПрименение статического анализа кода в преподавании и в разработке свободного ПО
Применение статического анализа кода в преподавании и в разработке свободного ПО
 
Автоматическое тестирование. Моя система
Автоматическое тестирование. Моя системаАвтоматическое тестирование. Моя система
Автоматическое тестирование. Моя система
 
Static code analysis of the projects built on Unreal Engine
Static code analysis of the projects built on Unreal EngineStatic code analysis of the projects built on Unreal Engine
Static code analysis of the projects built on Unreal Engine
 
Статический анализ кода проектов, построенных на движке Unreal Engine
Статический анализ кода проектов, построенных на движке Unreal EngineСтатический анализ кода проектов, построенных на движке Unreal Engine
Статический анализ кода проектов, построенных на движке Unreal Engine
 
Лучшие практики на практике
Лучшие практики на практикеЛучшие практики на практике
Лучшие практики на практике
 
Инструмент ChangelogBuilder для автоматической подготовки Release Notes
Инструмент ChangelogBuilder для автоматической подготовки Release NotesИнструмент ChangelogBuilder для автоматической подготовки Release Notes
Инструмент ChangelogBuilder для автоматической подготовки Release Notes
 
Jbreak 2016: Твой личный Spring Boot Starter
Jbreak 2016: Твой личный Spring Boot StarterJbreak 2016: Твой личный Spring Boot Starter
Jbreak 2016: Твой личный Spring Boot Starter
 

More from Andrey Karpov

60 антипаттернов для С++ программиста
60 антипаттернов для С++ программиста60 антипаттернов для С++ программиста
60 антипаттернов для С++ программистаAndrey Karpov
 
60 terrible tips for a C++ developer
60 terrible tips for a C++ developer60 terrible tips for a C++ developer
60 terrible tips for a C++ developerAndrey Karpov
 
Ошибки, которые сложно заметить на code review, но которые находятся статичес...
Ошибки, которые сложно заметить на code review, но которые находятся статичес...Ошибки, которые сложно заметить на code review, но которые находятся статичес...
Ошибки, которые сложно заметить на code review, но которые находятся статичес...Andrey Karpov
 
PVS-Studio in 2021 - Error Examples
PVS-Studio in 2021 - Error ExamplesPVS-Studio in 2021 - Error Examples
PVS-Studio in 2021 - Error ExamplesAndrey Karpov
 
PVS-Studio in 2021 - Feature Overview
PVS-Studio in 2021 - Feature OverviewPVS-Studio in 2021 - Feature Overview
PVS-Studio in 2021 - Feature OverviewAndrey Karpov
 
PVS-Studio в 2021 - Примеры ошибок
PVS-Studio в 2021 - Примеры ошибокPVS-Studio в 2021 - Примеры ошибок
PVS-Studio в 2021 - Примеры ошибокAndrey Karpov
 
Make Your and Other Programmer’s Life Easier with Static Analysis (Unreal Eng...
Make Your and Other Programmer’s Life Easier with Static Analysis (Unreal Eng...Make Your and Other Programmer’s Life Easier with Static Analysis (Unreal Eng...
Make Your and Other Programmer’s Life Easier with Static Analysis (Unreal Eng...Andrey Karpov
 
Best Bugs from Games: Fellow Programmers' Mistakes
Best Bugs from Games: Fellow Programmers' MistakesBest Bugs from Games: Fellow Programmers' Mistakes
Best Bugs from Games: Fellow Programmers' MistakesAndrey Karpov
 
Does static analysis need machine learning?
Does static analysis need machine learning?Does static analysis need machine learning?
Does static analysis need machine learning?Andrey Karpov
 
Typical errors in code on the example of C++, C#, and Java
Typical errors in code on the example of C++, C#, and JavaTypical errors in code on the example of C++, C#, and Java
Typical errors in code on the example of C++, C#, and JavaAndrey Karpov
 
How to Fix Hundreds of Bugs in Legacy Code and Not Die (Unreal Engine 4)
How to Fix Hundreds of Bugs in Legacy Code and Not Die (Unreal Engine 4)How to Fix Hundreds of Bugs in Legacy Code and Not Die (Unreal Engine 4)
How to Fix Hundreds of Bugs in Legacy Code and Not Die (Unreal Engine 4)Andrey Karpov
 
Game Engine Code Quality: Is Everything Really That Bad?
Game Engine Code Quality: Is Everything Really That Bad?Game Engine Code Quality: Is Everything Really That Bad?
Game Engine Code Quality: Is Everything Really That Bad?Andrey Karpov
 
C++ Code as Seen by a Hypercritical Reviewer
C++ Code as Seen by a Hypercritical ReviewerC++ Code as Seen by a Hypercritical Reviewer
C++ Code as Seen by a Hypercritical ReviewerAndrey Karpov
 
The Use of Static Code Analysis When Teaching or Developing Open-Source Software
The Use of Static Code Analysis When Teaching or Developing Open-Source SoftwareThe Use of Static Code Analysis When Teaching or Developing Open-Source Software
The Use of Static Code Analysis When Teaching or Developing Open-Source SoftwareAndrey Karpov
 
Static Code Analysis for Projects, Built on Unreal Engine
Static Code Analysis for Projects, Built on Unreal EngineStatic Code Analysis for Projects, Built on Unreal Engine
Static Code Analysis for Projects, Built on Unreal EngineAndrey Karpov
 
Safety on the Max: How to Write Reliable C/C++ Code for Embedded Systems
Safety on the Max: How to Write Reliable C/C++ Code for Embedded SystemsSafety on the Max: How to Write Reliable C/C++ Code for Embedded Systems
Safety on the Max: How to Write Reliable C/C++ Code for Embedded SystemsAndrey Karpov
 
The Great and Mighty C++
The Great and Mighty C++The Great and Mighty C++
The Great and Mighty C++Andrey Karpov
 
Static code analysis: what? how? why?
Static code analysis: what? how? why?Static code analysis: what? how? why?
Static code analysis: what? how? why?Andrey Karpov
 
Zero, one, two, Freddy's coming for you
Zero, one, two, Freddy's coming for youZero, one, two, Freddy's coming for you
Zero, one, two, Freddy's coming for youAndrey Karpov
 

More from Andrey Karpov (20)

60 антипаттернов для С++ программиста
60 антипаттернов для С++ программиста60 антипаттернов для С++ программиста
60 антипаттернов для С++ программиста
 
60 terrible tips for a C++ developer
60 terrible tips for a C++ developer60 terrible tips for a C++ developer
60 terrible tips for a C++ developer
 
Ошибки, которые сложно заметить на code review, но которые находятся статичес...
Ошибки, которые сложно заметить на code review, но которые находятся статичес...Ошибки, которые сложно заметить на code review, но которые находятся статичес...
Ошибки, которые сложно заметить на code review, но которые находятся статичес...
 
PVS-Studio in 2021 - Error Examples
PVS-Studio in 2021 - Error ExamplesPVS-Studio in 2021 - Error Examples
PVS-Studio in 2021 - Error Examples
 
PVS-Studio in 2021 - Feature Overview
PVS-Studio in 2021 - Feature OverviewPVS-Studio in 2021 - Feature Overview
PVS-Studio in 2021 - Feature Overview
 
PVS-Studio в 2021 - Примеры ошибок
PVS-Studio в 2021 - Примеры ошибокPVS-Studio в 2021 - Примеры ошибок
PVS-Studio в 2021 - Примеры ошибок
 
PVS-Studio в 2021
PVS-Studio в 2021PVS-Studio в 2021
PVS-Studio в 2021
 
Make Your and Other Programmer’s Life Easier with Static Analysis (Unreal Eng...
Make Your and Other Programmer’s Life Easier with Static Analysis (Unreal Eng...Make Your and Other Programmer’s Life Easier with Static Analysis (Unreal Eng...
Make Your and Other Programmer’s Life Easier with Static Analysis (Unreal Eng...
 
Best Bugs from Games: Fellow Programmers' Mistakes
Best Bugs from Games: Fellow Programmers' MistakesBest Bugs from Games: Fellow Programmers' Mistakes
Best Bugs from Games: Fellow Programmers' Mistakes
 
Does static analysis need machine learning?
Does static analysis need machine learning?Does static analysis need machine learning?
Does static analysis need machine learning?
 
Typical errors in code on the example of C++, C#, and Java
Typical errors in code on the example of C++, C#, and JavaTypical errors in code on the example of C++, C#, and Java
Typical errors in code on the example of C++, C#, and Java
 
How to Fix Hundreds of Bugs in Legacy Code and Not Die (Unreal Engine 4)
How to Fix Hundreds of Bugs in Legacy Code and Not Die (Unreal Engine 4)How to Fix Hundreds of Bugs in Legacy Code and Not Die (Unreal Engine 4)
How to Fix Hundreds of Bugs in Legacy Code and Not Die (Unreal Engine 4)
 
Game Engine Code Quality: Is Everything Really That Bad?
Game Engine Code Quality: Is Everything Really That Bad?Game Engine Code Quality: Is Everything Really That Bad?
Game Engine Code Quality: Is Everything Really That Bad?
 
C++ Code as Seen by a Hypercritical Reviewer
C++ Code as Seen by a Hypercritical ReviewerC++ Code as Seen by a Hypercritical Reviewer
C++ Code as Seen by a Hypercritical Reviewer
 
The Use of Static Code Analysis When Teaching or Developing Open-Source Software
The Use of Static Code Analysis When Teaching or Developing Open-Source SoftwareThe Use of Static Code Analysis When Teaching or Developing Open-Source Software
The Use of Static Code Analysis When Teaching or Developing Open-Source Software
 
Static Code Analysis for Projects, Built on Unreal Engine
Static Code Analysis for Projects, Built on Unreal EngineStatic Code Analysis for Projects, Built on Unreal Engine
Static Code Analysis for Projects, Built on Unreal Engine
 
Safety on the Max: How to Write Reliable C/C++ Code for Embedded Systems
Safety on the Max: How to Write Reliable C/C++ Code for Embedded SystemsSafety on the Max: How to Write Reliable C/C++ Code for Embedded Systems
Safety on the Max: How to Write Reliable C/C++ Code for Embedded Systems
 
The Great and Mighty C++
The Great and Mighty C++The Great and Mighty C++
The Great and Mighty C++
 
Static code analysis: what? how? why?
Static code analysis: what? how? why?Static code analysis: what? how? why?
Static code analysis: what? how? why?
 
Zero, one, two, Freddy's coming for you
Zero, one, two, Freddy's coming for youZero, one, two, Freddy's coming for you
Zero, one, two, Freddy's coming for you
 

Комплексное использование анализаторов для повышения качества кода