AUTOSAR C++14 Rule A14-5-3

Типовой оператор лица, не являющегося членом какой-либо организации, должен только быть объявлен в пространстве имен, которое не содержит класс (struct) тип, перечислимый тип или описания типа объединения

Описание

Управляйте определением

Типовой оператор лица, не являющегося членом какой-либо организации, должен только быть объявлен в пространстве имен, которое не содержит класс (struct) тип, перечислимый тип или описания типа объединения.

Объяснение

Это правило запрещает помещающие типовые операторы в том же пространстве имен как класс (struct) тип, перечислимый тип или описания типа объединения. Если класс, перечисление или типы объединения используются в качестве параметров шаблона, присутствие типовых операторов в том же пространстве имен может вызвать неожиданные разрешения вызова.

Считайте пространство имен NS это комбинирует класс B и типовая форма operator==:

namespace NS {
   class B {};
   template <typename T> bool operator==(T, std::int32_t);
}
Если вы используете класс B как параметр шаблона для другого типового класса, такого как этот шаблонный класс A:
template <typename T> class A {
    public:
      bool operator==(std::int64_t);
}

template class A<NS::B>;
целое пространство имен NS используется для разрешения перегрузки когда операторы класса A называются. Например, если вы вызываете operator== с int32_t аргумент, типовой operator== в пространстве имен NS с int32_t параметр используется вместо operator== в исходном шаблонном классе A с int64_t параметр. Вы или другой разработчик или рецензент кода можете ожидать, что вызов оператора решит к operator== в исходном шаблонном классе A.

Реализация Polyspace

Для каждого типового оператора средство проверки правила определяет, содержит ли содержание пространства имен также объявления типов классов, перечислимых типов или типов объединения. Если такое объявление найдено, средство проверки отмечает нарушение правила на самом операторе.

Средство проверки также отмечает типовые операторы, заданные в глобальном пространстве имен, если глобальное пространство имен также имеет класс, перечисление или объявления объединения.

Поиск и устранение проблем

Если вы ожидаете нарушение правила, но не видите его, обратитесь к Кодированию Стандартных Нарушений, Не Отображенных.

Примеры

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

#include <cstdint>

template <typename T> class Pair {
    std::int32_t item1;
    std::int32_t item2;
    public:
      bool operator==(std::int64_t ItemToCompare);
      bool areItemsEqual(std::int32_t itemValue) {
          return (*this == itemValue);
      }
};

namespace Operations {
    class Data {};
    template <typename T> bool operator==(T, std::int32_t); //Noncompliant
}

namespace Checks {
    bool checkConsistency();
    template <typename T> bool operator==(T, std::int32_t); //Compliant
}

template class Pair<Operations::Data>;

В этом примере, пространство имен Operations нарушает правило, потому что оно содержит тип класса Data вместе с типовым operator==. Пространство имен Checks не нарушает правило потому что единственное другое объявление в пространстве имен, помимо типового operator==, объявление функции.

В методе areItemsEqual в template class Pair<Operations::Data>, == операция вызывает типовой operator== метод в Operations пространство имен. Вызов решает к этому operator== метод на основе типа данных аргумента (std_int32_t). Этот метод является лучшим соответствием по сравнению с operator== метод в исходном шаблонном классе Pair.

Проверяйте информацию

Группа: шаблоны
Категория: консультация, автоматизированная