Scalars, Arrays, and Hashes
Perl has exactly three built-in data structure types, and it tells them apart with a sigil, a leading punctuation character on every variable name: a dollar sign $ marks a scalar, which holds a single value such as a number, string, or reference; an at sign @ marks an array, an ordered, indexed list of scalars; and a percent sign % marks a hash, an unordered collection of key-value pairs. Crucially, the sigil describes how many values you are accessing right now rather than the variable's declared type, so @fruits refers to the whole array but $fruits[0] refers to a single scalar element pulled out of that same array, and this consistent rule is one of the first things that trips up newcomers coming from languages with a single, uniform indexing syntax.
Cricket analogy: Similar to how a scoreboard shows a single current total (a scalar) alongside the full over-by-over list of runs (an array), Perl's $ and @ sigils tell you whether you're looking at one value or the whole list.
Scalars
A scalar variable, declared with my $name = 'Alice';, holds exactly one piece of data at a time, and Perl does not require you to declare whether that data is a number or a string; the same scalar can hold 42, 'hello', a floating-point number like 3.14, or even a reference to an array or hash. Perl automatically converts between numbers and strings depending on context, so my $count = '5' + 3; yields 8 because the + operator forces numeric context, while my $greeting = 'Item ' . 5; yields the string 'Item 5' because the . concatenation operator forces string context; this implicit conversion is powerful but is also why use warnings; is valuable, since it will flag things like adding a non-numeric string to a number.
Cricket analogy: Similar to how a single stat, a batter's current strike rate, can be read either as a plain number for a ranking table or embedded into a sentence for commentary, a Perl scalar like $runs shifts between numeric and string context automatically.
Arrays
An array, declared as my @colors = ('red', 'green', 'blue');, is a zero-indexed ordered list, so $colors[0] is 'red' and $colors[-1] conveniently returns the last element, 'blue', without needing to know the array's length. Arrays grow and shrink dynamically: push @colors, 'yellow'; appends an element, pop @colors; removes and returns the last one, and scalar @colors (or simply using @colors in a place that expects a number) tells you how many elements it holds. A common beginner mistake is writing $colors instead of $colors[0] when trying to grab the first element, since Perl will not automatically assume you meant the first element; $colors alone actually refers to a completely separate, unrelated scalar variable in Perl's namespace.
Cricket analogy: Similar to a batting order being a numbered list where slot 0 is the opener and the last slot is the number 11 batter, a Perl array is zero-indexed so $order[0] is the opener and $order[-1] is the last batter without counting manually.
Hashes
A hash, declared as my %ages = (Alice => 30, Bob => 25);, stores unordered key-value pairs where every key is a unique string and every value is a scalar, so $ages{Alice} retrieves 30 using curly braces rather than the square brackets used for arrays. The keys %ages function returns a list of all the keys, values %ages returns a list of all the values in the same corresponding order, and exists $ages{Carol} lets you safely check whether a key is present before accessing it, which avoids the subtle bug of auto-vivifying a new key with an undef value just by testing if ($ages{Carol}). Because hashes have no guaranteed order, code that needs a predictable iteration order should explicitly sort the keys, for example for my $name (sort keys %ages) { ... }, rather than relying on the order keys happen to come back in.
Cricket analogy: Similar to a scorecard mapping each player's name to their runs scored, where you look up 'Kohli' directly rather than searching a numbered list, a Perl hash $scores{Kohli} retrieves a value by name key instead of by position.
use strict;
use warnings;
# Scalar
my $name = 'Alice';
# Array
my @colors = ('red', 'green', 'blue');
push @colors, 'yellow';
print "First: $colors[0], Last: $colors[-1], Count: " . scalar(@colors) . "\n";
# Hash
my %ages = (Alice => 30, Bob => 25);
$ages{Carol} = 28;
for my $person (sort keys %ages) {
print "$person is $ages{$person} years old\n";
}
A handy mnemonic: the sigil always matches what you're pulling OUT, not what you started with. @colors is a whole array, but $colors[0] (one element) and $#colors (the last index number) both use $ because each expression yields a single scalar value.
- Perl has three core data types, distinguished by sigil: scalar ($), array (@), and hash (%).
- A scalar holds one value at a time and Perl converts freely between numeric and string context based on the operator used.
- Arrays are zero-indexed ordered lists;
$array[-1]conveniently accesses the last element without checking the length first. - push, pop, shift, and unshift are the standard functions for adding and removing elements from either end of an array.
- Hashes store unordered key-value pairs, accessed with curly braces like
$hash{key}, unlike the square brackets used for arrays. keys %hashandvalues %hashreturn corresponding lists;existssafely checks for a key without creating it.- Since hash order is not guaranteed, use
sort keys %hashwhen you need predictable iteration order.
Practice what you learned
1. Which sigil is used to access a single element of an array in Perl?
2. What does `$colors[-1]` return for an array @colors?
3. How do you access the value for key 'Alice' in a hash %ages?
4. What does `my $count = '5' + 3;` evaluate to in Perl?
5. Why should you use `exists $hash{key}` instead of `if ($hash{key})` to test for a key's presence?
Was this page helpful?
You May Also Like
Perl Operators
A tour of Perl's arithmetic, string, comparison, logical, and assignment operators, and the pitfalls of mixing numeric and string comparisons.
Your First Perl Script
A hands-on walkthrough of structuring, running, and debugging a complete beginner Perl script that reads, processes, and prints data.
What Is Perl?
An introduction to Perl's history, design philosophy, and the kinds of real-world problems it is still used to solve today.
Related Reading
Related Study Notes in Programming
Browse all study notesApache Spark Study Notes
Programming · 30 topics
ProgrammingApache Flink Study Notes
Programming · 30 topics
ProgrammingHadoop Study Notes
Programming · 30 topics
ProgrammingSnowflake Study Notes
Programming · 30 topics
ProgrammingApache Airflow Study Notes
Programming · 30 topics
Programmingdbt (Data Build Tool) Study Notes
Programming · 30 topics