in reply to RegEx Blues

. means "any one character".
\. means "one period".
You keep using the wrong one.

You used (XXX)+ where you mean (XXX+).

Then there's using $2 when the regexp only has one capture.

You didn't create any records for interfaces with no descriptions (but your desired output indicates you want this).

$Recs is a more accurate name for $Rec.

The XXX, XXX if XXX syntax is unusual and therefore harder to read.

Recs has no reason for being a hash reference. A hash is sufficient.

Your indenting is inconsistent. Pick a style and stick with it.

use warnings was missing. It would have identified your problems here.

use strict; use warnings; my %Recs; my $pc_name; while (<DATA>) { if (/interface (\S+)$/) { $pc_name = $1; $Recs{$pc_name} = {}; # Create record. next; } if (/switchport description (.*)$/) { $Recs{$pc_name}{description} = $1; next; } } for $pc_name (keys %Recs) { my $description = $Recs{$pc_name}{description}; if (defined $description) { $description = "switchport description $description"; } else { $description = ""; } print("interface $pc_name = switchport description $description\n" +); }
or if you're not planning on capturing more than just the description:
use strict; use warnings; my %descriptions; my $pc_name; while (<DATA>) { if (/interface (\S+)$/) { $pc_name = $1; $descriptions{$pc_name} = undef; next; } if (/switchport description (.*)$/) { $descriptions{$pc_name} = $1; next; } } for $pc_name (keys %descriptions) { my $description = $descriptions{$pc_name}; if (defined $description) { $description = "switchport description $description"; } else { $description = ""; } print("interface $pc_name = switchport description $description\n" +); }

Update: Added missing paren.

Update: Added creation of records with no description.