Perl chr Function

The chr function is used to convert ASCII or Unicode values into their corresponding characters.

The Perl chr function is used to convert ASCII or Unicode values into their equivalent characters. The reverse of this function is the ord function which is used to convert a character to its ASCII or Unicode value.

Two syntax forms are available for the chr function:

chr EXPR
chr

This function:

  • has as argument a number or an expression which after evaluation will return a number
  • returns the character represented by the EXPR

If chr function has no argument, the $_ is used instead.

See the following simple example of the chr function usage:

#!/usr/local/bin/perl
 
use strict;
use warnings;
 
print chr(65), "\n";
# it displays: A
 
print chr(0x41), "\n";
# it displays: A
 
my $str = chr(0x263a);
print length $str, "\n";
# it displays: 1 (character context)
 
{
  use bytes;
  print length $str, "\n";
  # it displays: 3 (bytes pragma context)
}
The line of code:
 
my $str = chr(0x263a);
initializes the $str with the 0x263a hexadecimal value which is a Unicode smiley face. Please note that the length of a single character held in $str is 1 because the length function acts in a character context.

However, if the length is calculated within the scope of the bytes pragma, the result will be returned in bytes – in our example 3.

Instead of using Perl chr function to initialize a string with Unicode characters, you can use hexadecimal escapes.

A hexadecimal escape begins with \x and it is either followed by a two digit hexadecimal number (for example "\x30" is "0") or a hexadecimal of arbitrary length included in curly braces (\x{263a}).

So, you could write:

my $str = "\x{263a}";
instead of:
 
my $str = chr(0x263a);
 

The following example shows you how to use the chr function in conjunction with the split, map and join functions.

See the following code snippet:

#!/usr/local/bin/perl
 
use strict;
use warnings;
 
# initialize a string
my $str = "72 101 108 108 111 32 87 111 114 108 100 33";
 
# split the string into an array of characters
my @array = split / /,$str;
 
# converts the elements of the array into characters
@array = map (chr, @array);
 
# join the elements of the array into the $str
$str = join "",@array;
 
# finnaly, print the string
print "$str\n";
# it outputs: Hello World!

I want to make a few considerations about this code:

  • the $str scalar variable is initialized with a sequence of ASCII codes, separated by space
  • the split function is used with the space pattern (" ") delimiter and it will return an array with the ASCII codes
  • the map function will run the Perl chr function for each element of the @array; at each iteration step the current element is assigned in turn to $_ and next the Perl chr function will act against the special variable $_; the map function returns the same array but having characters as elements
  • the @array elements will be concatenated into $str by using the join function without any delimiter ("")

The one-line map function:

@array = map (chr, @array);

can be rewritten with any of the following code lines:

@array = map (chr $_, @array);
@array = map { chr } @array;
@array = map { chr $_ } @array;

By the way, calling the map function with the expression syntax form is faster than calling it with the block syntax form.

A quicker alternative to do this is by using the pack function, as in the following example:

#!/usr/local/bin/perl
 
use strict;
use warnings;
 
my $str = "72 101 108 108 111 32 87 111 114 108 100 33";
 
# split the string into an array of characters
my @array = split / /,$str;
$str = pack("C*", @array);
print "$str\n";
# it displays: Hello World!

Please note that there is an important difference between the Perl chr and the pack functions. Whereas chr works on characters, the pack "C" function works on bytes. If you use the standard ASCII character set, you’ll get the same result.

But if you use Unicode, the pack function will behave the same meanwhile the Perl chr function will deal with the full Unicode character, which may be longer than 1 byte.

See the following snippet code:

#!/usr/local/bin/perl
 
use strict;
use warnings;
 
my $str = "48656c6c6f20576f726c6421";
 
$str =~ s/([a-fA-F0-9][a-fA-F0-9])/chr(hex($1))/eg;
print $str, "\n";
# it displays: Hello World!
In the above example:
  • the $str scalar variable is initialized with a few 2-digit hexadecimal values
  • in order to convert the hex string stored in $str to a character string the s/// substitution operator is used:
    • ([a-fA-F0-9][a-fA-F0-9]) match any two hexadecimal digits and store them in $1 - the using of round parentheses allow us to store the matched expression in the special variable named $1 and if you have more parentheses, the expression included in the second parenthesis will be assigned to $2, and so on
    • chr(hex($1)) is the replacement argument of the substitution operator; the hex function will convert the hexadecimal string stored in $1 in its decimal corresponding value and it will return this value; the Perl chr function will return the character represented by the numeric value returned by the hex function
    • e is a modifier and it tells the regex engine to treat the replacement field as Perl code
    • g is a modifier and tells the regex engine to repeatedly apply the substitution for all the characters of the string, starting with the first one

Finally, the content of the $str is printed, so the output will be:

Hello World!