exponenta event banner

Операция перемещения может вызвать

Операции перемещения могут привести к созданию контейнеров STL с использованием соответствующих операций копирования

Описание

Этот дефект возникает, когда класс явно объявляет конструктор перемещения, в котором отсутствует noexcept спецификатор или имеет noexcept спецификатор, аргумент которого вычисляется как false. Дефект также возникает, если явно объявленный конструктор перемещения имеет throw(type) спецификация исключения (устарела в C++ 11 и удалена в C++ 17).

Средство проверки не поднимает флаг, если конструктор перемещения неявно объявлен или явно объявлен как =default.

Риск

Если операция перемещения может вызвать исключения, некоторые контейнеры STL будут использовать операции копирования и не получат преимуществ от операции перемещения. Например, осуществление std::vector::resize метод использует std::move_if_noexcept и выполняет операцию перемещения для изменения размера вектора, только если операция перемещения объявлена noexcept.

Зафиксировать

Добавить noexcept спецификатор для объявления конструктора перемещения.

Если конструктор перемещения содержит выражения, которые могут вызвать, исправьте эти выражения. Выявление нарушений noexcept спецификация исключения, используйте средство проверки Noexcept function exits with exception.

Повышение производительности может зависеть от используемого компилятора, реализации библиотеки и среды.

Примеры

развернуть все

#include <string>

class Database {
  private:
      std::string* initEntry;
      int size;
  public:
      //Copy constructor
      Database (const Database& other);
      //Move constructor
      Database (Database&& other): initEntry{other.initEntry}, size{other.size} {
      other.initEntry = nullptr;
      other.size = 0;
    }
};

В этом примере Database конструктор перемещения не имеет noexcept спецификация.

Исправление - Добавить noexcept Спецификатор

Добавить noexcept спецификатор конструктора перемещения.

#include <string>

class Database {
   private:
       std::string* initEntry;
       int size;
   public:
       //Copy constructor
       Database (const Database& other);
       //Move constructor
       Database (Database&& other) noexcept: initEntry{other.initEntry}, size{other.size} {
       other.initEntry = nullptr;
       other.size = 0;
       }
};

Информация о результатах

Группа: Производительность
Язык: C++
По умолчанию: Откл.
Синтаксис командной строки: MOVE_OPERATION_MAY_THROW
Воздействие: Низкий
Представлен в R2020b