Skip to content

Latest commit

 

History

History

sub1

Folders and files

NameName
Last commit message
Last commit date

parent directory

..
 
 

2.4.1 Присваивание кортежу

Другая форма присваивания, известная как присваивание кортежу, позволяет выполнять присваивание значений нескольким переменным одновременно.

Прежде чем любая из переменных в левой части получит новое значение, вычисляются все выражения из правой части. Это делает эту разновидность присваивания наиболее полезной, когда некоторые переменные встречаются с обеих сторон оператора присваивания, например, при обмене значений двух переменных:

x, y, = y, x
a[i], a[j] = a[j], a[i]

Или при вычислении наибольшего общего делителя двух целых чисел:

func gcd(x, y, int) int {
    for y != 0 {
        x, y, = y, x%y
    }
    return x
}

Или при итеративном вычислении n-1-го числа Фибоначчи:

func fib(n int) int {
    x, y, := 0, 1
    for i := 0; i < n; i++ {
        x, y = y, x+y
    }
    return x
}

Присваивание кортежу может также сделать последовательность присваиваний более компактной:

i, j, k = 2, 3, 5

При этом (в качестве вопроса стиля) следует избегать присваивания кортежам при наличии сложных выражений: последовательность отдельных инструкций читается легче.

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

f, err = os.Open("foo.txt") // Вызов функции возвращает два значения

Зачастую функции используют дополнительные результаты для указания произошедшей ошибки, возвращая значение error, как в случае с вызовом функции os.Open(), либо значение типа bool, обычно с именем ok.

Если в присваивании, в котором ожидаются два результата, находится поиск по карте, утверждение о типе или получение из канала - создается дополнительный логический результат:

v, ok = m[key] // Поиск по карте
v, ok = x.(T) // Утверждение о типе
v, ok = <- ch // Получение из канала

Как и в случае объявления переменных, мы можем присвоить ненужные значения пустому идентификатору:

_, err = io.Copy(dst, src) // Отбрасываем количество байтов
_, ok, x.(T) // Проверка типа, игнорируем результат

Выводы:

  • Присваивание кортежу - это метод, который позволяет присваивать значения нескольким переменным одновременно, делая код более компактным и понятным;
  • Все выражения справа вычисляются перед присваиванием значений переменным слева, что позволяет обменивать значения переменных, например, вычислять наибольший общий делитель или числа Фибоначчи:
    • func fib(n int) int {
        x, y, := 0, 1
        for i := 0; i < n; i++ {
            x, y = y, x+y
        }
        return x
      }
  • Присваивание кортежу удобно для обмена значений между переменными, такими как x, y = y, x или a[i], a[j] = a[j], a[i];
  • Для функций с несколькими результатами присваивание кортежу используется для того, чтобы присвоить значения каждому из результатов, например: f, err = os.Open("foo.txt");
  • Дополнительные результаты функций часто используются для указания на ошибки, возвращая значение error или булево значение ok;
  • В присваивании кортежу можно использовать пустой идентификатор _, чтобы игнорировать ненужные значения, например: _, err = io.Copy(dst, src);
  • Присваивание кортежу повышает читаемость и понятность кода, но нужно избегать его использования при наличии сложных выражений, так как последовательность отдельных инструкций может быть легче для чтения.