ITworld.com
  Search  
ITworld Home Page ITworld Webcasts ITworld White Papers ITworld Newsletters ITworld News ITworld Topics Careers ITworld Voices ITwhirled Changing the way you view IT
Repeating Yourself: The X Operator
PERL --- 09/20/2001

Andrew Johnson

Loops are the general mechanism for expressing repetition in code. However, there are a couple of instances where loops seem like overkill -- repeating strings and repeating lists. For these cases, Perl provides the repetition operator (the 'x' operator).

In the case of a repeated string, we may simply want to print out lines of 20 '-' characters (perhaps as boundary lines in a report). Doing this with a loop is not difficult, though a little cumbersome given the task:

print "This is the Header\n";
print '-' for 1 .. 20; print "\n";

The x operator allows us to build this string in a single operation:

print "This is the Header\n";
print '-' x 20, "\n";

The x operator is a binary operator (takes two operands) and is context sensitive both in terms of the context of the entire operation, and in terms of the context of the left operand). The basic syntax is:

Left-EXPR x Right-EXPR

The right expression (right operand) is always considered to be in scalar context and treated as an integer. The left expression (left operand) may be either a scalar or a list value.

When the left operand is a scalar, as in the example above, the x operator treats it as a string and returns a new string repeated by the number given as the right operand. So, '-' x 20 returns a string of 20 '-' characters, and 'foo' x 2 returns the string 'foofoo'. This evaluation remains the same whether the entire expression is in scalar context or in list context --- in the example above the expression is an argument to the print() function and therefore in list context.

The x operator can return repeated lists if used in list context and if the left operand is a literal list (i.e., wrapped in parentheses):

my @array = (1,2,3) x 2;
print "@array" # prints: 1 2 3 1 2 3

You need to be careful to put the left operand in parentheses for list repetition --- using a plain array will not behave as desired:

my @array = (1,12,42);
@array = @array x 2; print "@array\n"; # prints: 33

In this case, because the left operand is not in parentheses it is evaluated as a scalar, and an array in scalar context returns the number of elements in the array --- in this case 3 --- thus the x operator has returned the string '3' repeated twice.

Is this operator practical? Consider a case where you want to define a ten-element array and initialize each element to 1:

my @array = (1) x 10; # my @array = (1,1,1,1,1,1,1,1,1,1);

Another useful case is initializing a hash when we've read in (or otherwise obtained) a list of keys we wish to initialize to 1:

my @keys = qw(a b c d);
my %hash; @hash{@keys} = (1) x @keys;

Lastly, a minor cautionary note --- remember that 'x' is not the multiplication operator:

my $value = 15 x 2 / 3;
print "$value\n"; # prints: 505

Here the number 15 is treated as a string and repeated twice to get 1515 which is then treated as a number and divided by 3 to get 505 (rather than the result of 10 you might have wanted). This is one case where Perl's natural conversion between numbers and strings without warning can mean that a simple typo ('x' instead of '*') can lead to strange results and is difficult to track down. So, if you have calculations in your code and you are getting bizarre results you might want to check for this particular typo.

 

Andrew Johnson works as a programmer/consultant and is the author of Elements of Programming with Perl from Manning Publications.



 Home   Newsletters  PERL
www.itworld.com    open.itworld.com     security.itworld.com     smallbusiness.itworld.com
storage.itworld.com     utilitycomputing.itworld.com     wireless.itworld.com

 
Contact Us   About Us   Privacy Policy    Terms of Service   Reprints  

CIO   Computerworld   CSO   GamePro   Games.net   Industry Standard   Infoworld   ITworld  
JavaWorld   LinuxWorld  MacUser   Macworld   Network World   PC World   Playlist  

DEMO   IDG Connect   IDG Knowledge Hub   IDG TechNetwork   IDG World Expo  

Copyright © Computerworld, Inc. All rights reserved

Reproduction in whole or in part in any form or medium without express written permission of Computerworld Inc. is prohibited. Computerworld and Computerworld.com and the respective logos are trademarks of International Data Group Inc.