AUTOSAR C++14 Rule A12-8-7

Операторы присваивания должны быть объявлены с касательно спецификатора &

Описание

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

Операторы присваивания должны быть объявлены с касательно спецификатора &.

Объяснение

Можно использовать касательно спецификаторов, чтобы задать, применяются ли функция или оператор к lvalues или rvalues. Функции или операторы, которые применяются к lvalues, имеют & касательно спецификатора. Функции и операторы, которые применяются на rvalues, имеют && касательно спецификатора в конце их объявления.

Встроенные операторы присваивания на C++ принимают только lvalues как входные параметры. Если пользовательские операторы присваивания берут и rvalue и lvalue как входные параметры, это может вызвать беспорядок и ошибки. Рассмотрите этот код где пользовательский оператор присваивания для класса obj принимает и rvalues и lvalues как входные параметры.

class obj{
	obj& operator=(Obj const&){
		//...
		return *this;
	}
	//...
};

int main(){
	int i,j,k;
	obj a,b,c;

	if((i+j)=k) // compilation error
	//...
	if((a+b)=c) // silent error
	//...
}

  • В первом if оператор, равное - к оператору (==) записан как оператор присваивания (=) из-за типографской ошибки. Поскольку встроенный оператор присваивания для int не принимает rvalues как вход, оператор (i+j) = k вызывает ошибку компиляции.

  • Условие для второго if оператор содержит подобную ошибку. Поскольку пользовательский оператор присваивания для класса obj принимает и lvalues и rvalues, как введено, оператор (a+b) = c компиляции без ошибки. if блок неожиданно выполняется, приводя к тихой ошибке.

Чтобы избежать ошибок и беспорядка, укажите, что операторы присваивания берут только lvalues в качестве входных параметров путем добавления & касательно спецификатора к их объявлению.

Реализация Polyspace

Polyspace® отмечает пользовательское присвоение, составное присвоение, шаг и операторы понижения когда:

  • У них нет & касательно спецификатора в их объявлении.

  • Они - функции членства класса.

  • Они не объявляются как = delete.

Поскольку касательно спецификаторов применимы только к нестатическим функциям членства, это правило не применяется к операторам присваивания лица, не являющегося членом какой-либо организации.

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

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

Примеры

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

В этом примере показано, как Polyspace отмечает операторы присваивания и инкрементные или операторы понижения, когда их объявления не задают & касательно спецификатора.

#include<cstdint>
class Obj
{
public:
	Obj() = default;
	Obj& operator=(Obj const&) & = default; //Compliant    
	Obj& operator=(Obj&&) & = default;      //Compliant    
	Obj& operator++() & noexcept;           //Compliant    
	Obj& operator--()  noexcept;            //Noncompliant 
	Obj& operator<<=(Obj const&) noexcept;  //Noncompliant   
	Obj& operator>>=(Obj const&) & noexcept;//Compliant   
	Obj& operator+=(Obj const&)&;           //Compliant
	Obj& operator-=(Obj const&);            //Noncompliant
	Obj& operator*=(Obj const&)= delete;    //Compliant
	Obj& operator+(Obj const&)&;            //Compliant  
};

Obj& operator|=(Obj& f,const std::int32_t i) // Rule does not apply 
{
	return f;
}

Obj& Obj::operator+=(Obj const&) &  // Polyspace flags the declaration 
{
	return *this;
}
Obj F1() noexcept
{
	return Obj{};
}
int main()
{
	Obj c;
	//F1() += c; // Compilation Error
	//F1() = c; // Compilation Error
	F1() -= c; // Silent Bug
}

В main(), операторы присваивания +=, -=, и = используются с входом rvlaue. Поскольку объявления операторов += и = задайте & касательно спецификатора, использование этих операторов с rvalue ввело результаты в отказе компиляции. Оператор -= объявляется без ссылочного спецификатора &. Используя этот оператор с rvalue вход создает тихую ошибку.

  • Polyspace отмечает неудаленные операторы присваивания члена, инкрементные операторы и операторы понижения, которые не задают & касательно спецификатора в их объявлениях.

  • Когда оператор присваивания члена объявляется без ссылочного спецификатора & в классе и заданный в другом месте, Polyspace отмечает объявление.

  • Polyspace не отмечает операторы лица, не являющегося членом какой-либо организации, без & касательно спецификатора потому что это правило применяется только к нестатическим функциям членства.

  • Polyspace не отмечает удаленные операторы потому что с помощью & касательно спецификатора на удаленном операторе не оказывает влияния на код.

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

Группа: Специальные функции членства
Категория: консультация, автоматизированная
Введенный в R2020b