Thursday, May 17, 2007

Perl - Variable Interpolation for single quoted strings

A colleague was writing a perl script to print a string with embedded newlines in it. The string originated as a multi-line environment variable value i.e.

csh%> setenv Foo "a b c\nd e f"
csh %> echo $Foo
a b c
d e f
csh %>

csh %> perl -e 'print $ENV{Foo} . "\n";'
a b c\nd e f

The value of $ENV{Foo} was being interpreted as a singly quoted string and the \n was being automatically backslashed internally whenever variable interpolation took place.

index($ENV{Foo}, '\n') ; # returned 5
index($ENV{Foo}, "\\n") ; # returned 5

There are a couple of ways to solve this

% perl -e '$ENV{Foo} =~ s/\\n/\n/g; print $ENV{Foo} . "\n";'
% perl -e 'eval "\$f = \"" . $ENV{Foo} . "\""; print $f . "\n";'
( or in a script use: eval '$f = "'. $ENV{Foo} . '"'; )

I was hoping there are better ways to do this. The first solution uses the regular expression engine to match every character in the string with the pattern. The second solution uses eval!

Is there a perl hack that will force variable interpolation on a singly quoted string? I thought of unpack but didn't have enough time to look into it.

No comments: