Converting Between ASCII Characters and Values

Problem

You want to print out the number represented by a given ASCII character, or you want to print out an ASCII character given a number.

Solution

Use ord to convert a character to a number, or use chr to convert a number to a character:

$num  = ord($char);
$char = chr($num);

The %c format used in printf and sprintf also converts a number to a character:

$char = sprintf("%c", $num);                # slower than chr($num)
printf("Number %d is character %c\n", $num, $num);

                  Number 101 is character e

A C* template used with pack and unpack can quickly convert many characters.

@ASCII = unpack("C*", $string);
$STRING = pack("C*", @ascii);

Discussion

Unlike low-level, typeless languages like assembler, Perl doesn’t treat characters and numbers interchangeably; it treats strings and numbers interchangeably. That means you can’t just assign characters and numbers back and forth. Perl provides Pascal’s chr and ord to convert between a character and its corresponding ordinal value:

$ascii_value = ord("e");    # now 101
$character   = chr(101);    # now "e"

If you already have a character, it’s really represented as a string of length one, so just print it out directly using print or the %s format in printf and sprintf. The %c format forces printf or sprintf to convert a number into a character; it’s not used for printing a character that’s already in character format (that is, a string).

printf("Number %d is character %c\n", 101, 101);

The pack , unpack, chr, and ord functions are all faster than sprintf. Here are pack and unpack in action:

@ascii_character_numbers = unpack("C*", "sample");
print "@ascii_character_numbers\n";

                  115 97 109 112 108 101

$word = pack("C*", @ascii_character_numbers);
$word = pack("C*", 115, 97, 109, 112, 108, 101);   # same
print "$word\n";

                  sample

Here’s how to convert from HAL to IBM:

$hal = "HAL";
@ascii = unpack("C*", $hal);
foreach $val (@ascii) {
    $val++;                 # add one to each ASCII value
}
$ibm = pack("C*", @ascii);
print "$ibm\n";             # prints "IBM"

The ord function can return numbers from to 255. These correspond to C’s unsigned char data type.

See Also

The chr, ord, printf, sprintf, pack, and unpack functions in perlfunc(1) and Chapter 3 of Programming Perl

Get Perl Cookbook now with the O’Reilly learning platform.

O’Reilly members experience books, live events, courses curated by job role, and more from O’Reilly and nearly 200 top publishers.