Most programmers know you have to check return values from system
functions. Unless you’re just starting out as a programmer, you
know that this is bad:

open( my $fh, '<', 'something.txt' );
while ( my $line =  ) {
# do something with the input

If that open fails the program continues on. The call to
readline will fail, return undef as if we’re at
the end of the file, and the user will be none the wiser. If you
have use warnings on, you’ll get a “readline() on closed
filehandle”, but that’s not much help when you should be dying.
Instead, you should be opening your file like this:

my $filename = 'something.txt';
open( my $fh, '<', $filename ) or die "Can't open $filename: $!";

This way, your user gets a useful error message if something goes
wrong, but more importantly, the program doesn’t continue as if
nothing is wrong, potentially doing what it should not.
h2. GetOptions needs checking, too
Unfortunately, I see programs where otherwise-sensible programmers
ignore the return code of GetOptions.

use Getopt::Long;
'n=i' => my $count,
# Do something that uses $count
print "Processing complete!n";

There are any number of ways the user can call this program incorrectly:

$ perl foo -n
Option n requires an argument
Processing complete!
$ perl foo -n=five
Value "five" invalid for option n (number expected)
Processing complete!
$ perl foo -m=12
Unknown option: m
Processing complete!

In all three of these cases, the user made a mistake, but the program
lets it slide without a mention. The user’s going to be disappointed
with the results.
The solution is simple: Always check the results of GetOptions().
The easiest way is to task && exit(1) after the call:

use Getopt::Long;
'n=i' => my $count,
) or exit(1);

It’s simple, effective, and prevents unexpected sorrow.