Дополненное задание - Augmented assignment

Расширенное присваивание (или составное присваивание ) - это имя, данное определенным операторам присваивания в определенных языках программирования (особенно тех, которые являются производными от C ). Расширенное присваивание обычно используется для замены оператора, в котором оператор принимает переменную в качестве одного из своих аргументов, а затем присваивает результат обратно той же переменной. Простой пример расширен до . Подобные конструкции часто доступны для различных бинарных операторов. x += 1x = x + (1)

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

Обсуждение

Например, следующий оператор или его вариант можно найти во многих программах:

x = x + 1

Это означает «найти число, хранящееся в переменной x , прибавить к нему 1 и сохранить результат сложения в переменной x ». Каким бы простым это ни казалось, он может иметь неэффективность, так как местоположение переменной x нужно искать дважды, если компилятор не распознает, что две части выражения идентичны: x может быть ссылкой на некоторый элемент массива или другая сложность. Для сравнения, вот версия с расширенным назначением:

x += 1

В этой версии нет оправдания тому, что компилятор не смог сгенерировать код, который ищет местоположение переменной x только один раз и изменяет его на месте, если, конечно, машинный код поддерживает такую ​​последовательность. Например, если x - простая переменная, последовательность машинного кода может выглядеть примерно так:

 Load  x
 Add   1
 Store x

и для обеих форм будет создан один и тот же код. Но если есть специальный код операции, это может быть

 MDM   x,1

означает «Изменить память», добавив 1 к x, и приличный компилятор сгенерирует один и тот же код для обеих форм. Некоторые машинные коды предлагают операции INC и DEC (для добавления или вычитания единицы), другие могут допускать константы, отличные от единицы.

В более общем плане форма

x ?= expression

где ? обозначает некоторый оператор (не всегда + ), и не может быть никаких специальных кодов операций, которые могут помочь. По-прежнему существует вероятность того, что, если x - сложная сущность, компилятору будет рекомендовано избегать дублирования при доступе к x , и, конечно, если x - длинное имя, потребуется меньше ввода. Последнее было основой аналогичной функции в компиляторах ALGOL, предлагаемых через системы Burroughs B6700 , с использованием символа тильды для обозначения переменной, которой назначается, так что

LongName:=x + sqrt(LongName)*7;

станет

LongName:=x + sqrt(~)*7;

и так далее. Это более общий характер, чем просто x:=~ + 1;создание оптимального кода, оставшееся прерогативой компилятора.

Семантика

В языках программирования, ориентированных на выражения, таких как C, присваивание и расширенное присваивание - это выражения, которые имеют значение. Это позволяет использовать их в сложных выражениях. Однако это может привести к появлению последовательностей символов, которые трудно читать или понимать, и, что еще хуже, опечатка может легко привести к другой последовательности тарабарщины, которая, хотя и принята компилятором, не дает желаемых результатов. В других языках, таких как Python, присваивание и расширенное присваивание являются операторами, а не выражениями, и поэтому не могут использоваться в сложных выражениях. Например, следующий допустимый C, но не действительный Python:

a += b += c

Как и присваивание, в этих языках расширенное присваивание является формой правоассоциативного присваивания .

В отличие от C, выражения составного присваивания C ++ оценивают lvalue . Значение lvalue позволяет записать его слева от другого оператора присваивания:

int x = 11;
(x *= 2) += 3; // Sets x to 25

Вычисленные места назначения

В таких языках, как C, C ++ и Python, расширенному назначению, в котором место назначения включает вызовы функций, предписывается вызывать функции только один раз. Т.е. в заявлении:

my_array[f1()] += 1

Функция f1имеет мандат быть вызван только один раз.

Если язык реализует расширенное присвоение путем расширения макроса до:

my_array[f1()] = my_array[f1()] + 1

Затем f1вызывается дважды.

По языку

C потомки

В C , C ++ и C # оператор присваивания = , который дополняется следующим образом:

Оператор Описание
+= Добавление
-= Вычитание
*= Умножение
/= Разделение
%= Модуль
<<= Левый битовый сдвиг
>>= Правый битовый сдвиг
&= Побитовое И
^= Побитовое исключающее ИЛИ
|= Поразрядное включающее ИЛИ

Каждый из них на указанных языках называется составным оператором присваивания .

Поддерживающие языки

Следующий список, хотя и не полный и не исчерпывающий, перечисляет некоторые из основных языков программирования, поддерживающих расширенные операторы присваивания.

Смотрите также

использованная литература

  1. ^ a b «Операторы присваивания» . cppreference.com . Справочник по C ++ . Проверено 1 марта 2021 года .
  2. ^ Страуструп, Бьярне (2013). Язык программирования C ++ (Четвертое изд.). Эддисон-Уэсли. ISBN 978-0-321-56384-2.
  3. ^ "ISO / IEC 9899: проект комитета 201x от 12 апреля 2011 г. N1570" .
  4. ^ «Присваивание и составные операторы присваивания» .
  5. ^ «Спецификация языка C #» . Microsoft . Проверено 17 марта 2014 года .