Я пытаюсь реализовать сортировку слиянием в C, когда натолкнулся на что-то интересное, поднятое [Analyze -> Run Code Analysis] в Visual Studio 2015.
Код выглядит следующим образом:
void MergeSort_r(int A[], int n)
{
// A = {1, 3, 2}
// n = 3
int rightCount;
int* R;
if ( n < 2 ) return;
// version 1: rightCount = 2
rightCount = n - (n/2);
// version 2: rightCount = 2
rightCount = n - 1;
R = ( int* ) malloc( rightCount * sizeof( int ) );
if ( R ) {
for ( int i = 0; i < rightCount; i++ ) {
R[i] = A[i];
}
free( R );
}
}
Хотя обе версии rightCount по существу оцениваются как 2, в первой версии я получаю предупреждение:
«Переполнение буфера при записи в ‘R’: размер записи равен ‘(unsigned int) rightCount * sizeof (int)’ байтов, но может быть записано 8 байтов.»
Есть идеи, почему это так? Будем рады услышать ваши ответы.
Набор инструментов для анализа кода в Visual C ++ не всегда предлагает лучшие предупреждения. Он пытается дать вам лучший набор предупреждений, чтобы исправить некоторые потенциальные проблемы / ошибки, которые могут появиться во время выполнения. У вас есть несколько вариантов:
#pragma
директивы.new
, make_unique
и т.п.В идеале вы всегда должны использовать новые примитивы smart pointers, такие как unique_ptr
, shared_ptr
и т.д. Они не только выделяют память для вас, но и освобождают от любого исключения, выброшенного в стек вызовов. Вам не нужно вводить *
полностью!
auto buffer = make_unique<int[]>(10); // 10 integers
Ваш код в порядке, и инструменты (особенно анализаторы) имеют свои недостатки — иногда они генерируют ложные срабатывания. Это один из них. Кстати, я проверил ваш код на MSVS2015, и он не дает мне никаких предупреждений.