68. Типизированные хеши в Perl 6

Сегодня мы разберемся с типизированными хешами, но сначала позвольте напомнить, как указать тип простой скалярной переменной:

my Int $i;

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

> my Int @i;
[]

> @i.push(42);
[42]

Если попытаться в этот массив добавить строку, произойдет ошибка:

> @i.push('Hello');
Type check failed in assignment to @i;
expected Int but got Str ("Hello")
  in block <unit> at <unknown file> line 1

А вот с хешами чуть сложнее, потому что у каждого элемента хеша два элемента: ключ и значение.

Чтобы указать тип значений, используется вот такой синтаксис:

my Str %s;

Теперь мы можем хранить строки:

> %s<Hello> = 'World'
World

> %s<42> = 'Fourty-two'
Fourty-two

Но не числа:

> %s<x> = 100
Type check failed in assignment to %s;
expected Str but got Int (100)
  in block <unit> at <unknown file> line 1

(Обратите внимание, что ключом в %s<42> тоже является строка, а не число.)

А чтобы указать тип ключей, поставьте его имя в фигурных скобках:

my %r{Rat};

У нас получился типизированный, или объектный хеш.

Например, создадим хеш, где ключами будут работать значения типа Rat:

> %r<22/7> = pi
3.14159265358979

> %r
{22/7 => 3.14159265358979}

Теперь уже невозможно использовать ни целые числа, ни строки:

> %r<Hello> = 1
Type check failed in binding to parameter 'key';
expected Rat but got Str ("Hello")
  in block <unit> at <unknown file> line 1

> %r{23} = 32
Type check failed in binding to parameter 'key';
expected Rat but got Int (23)
  in block <unit> at <unknown file> line 1

И, наконец, еще более ограничим элементы хеша, указав одновременно и тип ключей, и тип значений:

my Str %m{Int};

Ключи здесь — целые числа, а значения — строки. Например, в этом хеше теперь можно хранить соответствие номеров месяцев их названиям, но не наоборот:

> %m{3} = 'March'
March

> %m<March> = 3
Type check failed in binding to parameter 'key';
expected Int but got Str ("March")
  in block <unit> at <unknown file> line 1

 

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google+ photo

You are commenting using your Google+ account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s