Использование std :: sort с указателями на целочисленные переменные приводит к неожиданному выводу - PullRequest
0 голосов
/ 24 февраля 2019

Я решил скомпилировать и запустить этот кусок кода (из любопытства), и компилятор G ++ успешно скомпилировал программу.Я ожидал увидеть ошибку компиляции или ошибки времени выполнения, или, по крайней мере, значения a и b поменялись местами (как 5> 1), так как функция std::sort() вызывается с двумя указателями на целые числа.(Обратите внимание, что я знаю, что это не очень хорошая практика, и я просто играл с указателями)

#include <iostream>
#include <algorithm>

int main() {
    int a{5};
    int b{4};
    int c{1};
    int* aptr = &a;
    int* bptr = &b;
    std::sort(aptr, bptr);
    std::cout << a << ' ' << b << ' ' << c << '\n';
    return 0;
}

Однако после выполнения программы я получил следующий вывод:

5 4 1

Мой вопрос: как C ++ разрешил этот вызов функции std::sort()?И как не получилось на самом деле отсортировать все между адресами памяти a и b (потенциально включая даже значения мусора в памяти)?

Я имею в виду, если мы попробовали это с массивами в стиле C, как это (std::sort(arr, arr+n)) он успешно отсортировал бы массив в стиле C, потому что arr и arr+n в основном просто указатели, где n - это размер массива, а arr - указатель на первый элемент.

(извините, если этот вопрос звучит глупо. Я все еще изучаю C ++.)

Ответы [ 2 ]

0 голосов
/ 24 февраля 2019

C ++ принимает ваш код как синтаксически правильный.Но это не работает, потому что sort (it1, it2) ожидает, что it1 - это начальная позиция массива, а it2 - конечная позиция того же массива.Вы предоставили два разных массива для функции сортировки, которая может привести к любой из двух следующих ситуаций:

positionof (it1) : предположим, что в массиве памяти компьютера a и bхранится в таком виде - 5 (а), -1, -2, 10, 4 (б).тогда функция сортировки будет сортировать от 5 до 4, что приведет к: -2 (a), - 1,4,5,10 (b).

positionof (it1)> positionof (it2) (случай вашей машины): функция сортировки ничего не сделает как left_position> right_position.

0 голосов
/ 24 февраля 2019

Ваша программа плохо сформирована, диагностика не требуется.Вы передали указатели, которые не образуют диапазон для алгоритма std.

Любое поведение программы соответствует стандарту C ++.

Компиляторы оптимизируют работу вокруг факта, что указатели на несвязанные объекты являютсянесопоставимы и их разница не определена.Сортировка здесь может привести к тому, что UB оптимизатор может исключить такие ветки, как сумасшедшие (поскольку любая ветка с UB может быть исключена и заменена альтернативной (независимо от того, какой код альтернативная ветвь является допустимым результатом UB)).

Таким образом, хороший стиль кодирования C ++ направлен на то, чтобы избегать кодирования UB и IL-NDR.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...