Name

Yet Another Perl 6 Operator: The Cross Operator

Version

Maintainer: Adriano Ferreira <ferreira@cpan.org>
Date: 21 Dec 2007
Last Modified: 21 Dec 2007
Number: 12
Version: 2
Status: Published
at ONLamp:
   published at: 21 Dec 2007
   url: http://www.oreillynet.com/onlamp/blog/2007/12/yap6_operator_the_cross_operat.html

Body

Perl 6 provides an operator 'X', the cross operator, which combines its list operands into a sort of cartesian product of these arguments.

1,2 X 3,4        # (1,3), (1,4), (2,3), (2,4)

1,2 X 3,4 X 5,6  # (1,3,5), (1,3,6), (1,4,5), ..., (2,4,6)

The 'X' operator returns all possible lists formed by taking one element from each of its list arguments. The ordering of the returned lists is such that the rightmost elements vary fastest. Hence,

<a b> X (1,2)

ends up with

('a', 1), ('a', 2), ('b', 1), ('b', 2)

where the first elements come from <a b> and the second elements from (1,2).

In @ (list) context, the result becomes a flat list, while in @@ (splice) context it turns into a list of arrays.

say @(<a b> X 1,2)
'a', 1, 'a', 2, 'b', 1, 'b', 2
say @@(<a b> X 1,2)
['a', 1], ['a', 2], ['b', 1], ['b', 2]

The operator is list associative, so that @a X @b X @c produce a list of three-element lists. If any of the lists is empty, you will end up with a null list.

The cross operator also plays nicely with unbounded lists. But only the leftmost argument can be usefully an infinite list, or else some elements (other than the first ones of the next arguments) will never be seen.

Just like the zip operator, the cross operator provides a handy operation on lists avoiding the need to code it with basic operations (like nested loops or maps). That avoids the need for clustered low-level coding when implementing some high-level algorithms.

For instance, data structures like rectangular boards can be generated from simple Perl 6 expressions, like:

# tic-tac-toe slots
0..^3 X 0..^3

# chess board squares
'a'..'h' X 1..8

See Also

The zip operator .

$Revision: 109 $