Курс языка программирования Raku / Продвинутый уровень / Контейнеры / Контексты

Элементный и списковый контекст

Два дополнительных контекста определяют, будет ли что-то рассматриваться как список из нескольких значений или как один элемент. В этом заключается различие между сигилами @ и $.

В контексте списка массив раскрывается в свои элементы. Цикл for помещает свой аргумент в контекст списка, поэтому он перебирает каждый элемент:

my @a = 1, 2, 3;

my $count = 0;
$count++ for @a;
say $count; # 3

В контексте элемента тот же массив рассматривается как одно единственное значение. Контекстуализатор $( … ) принудительно задаёт контекст элемента, поэтому цикл теперь видит только одну вещь и выполняется один раз:

my @a = 1, 2, 3;

my $count = 0;
$count++ for $(@a);
say $count; # 1

Вот почему присвоение массива скаляру упаковывает его как единый элемент, а не копирует его элементы: my $x = @a помещает @a в контекст элемента. Обратите внимание, что этот единственный элемент может быть другим контейнером с множеством элементов внутри:

my @a = 1, 2, 3;

my $var = @a;
say $var;      # [1 2 3]
say $var.WHAT; # (Array)

Переменная $var теперь содержит один (поскольку это скалярный контейнер) объект, который является Array. Вы можете легко убедиться в этом, обращаясь к $x как к своего рода ссылке на массив (как это называлось бы в других языках):

say $var[1]; # 2

Соответствующий контекстуализатор @( … ) делает обратное, принудительно задавая контекст списка.

Существует также контекст поглощения (sink context) — контекст выражения, значение которого отбрасывается, например, строка кода, существующая только ради побочного эффекта. Когда значение попадает в контекст поглощения без полезного применения, Raku может предупредить о «бесполезном использовании» (useless use), что является полезной подсказкой о том, что вы забыли использовать результат.

Сигил, который вы выбираете ($ или @), — это по сути выбор контекста, а контекстуализаторы $( ) и @( ) позволяют при необходимости его переопределить.

Практика

Пройдите 1 тест по содержанию этой темы.

Навигация по курсу

Тест — Контексты   |   Тест — Элементный контекст


💪 Или перейдите сразу к упражнениям этого раздела.