Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I use a perl variable name properly within backticks?

I need to execute the following code on a bash shell:

mogrify -resize 800x600 *JPG

Since the width and height are variables, I tried this:

`mogrify -resize $widx$hit *JPG`

However in compilation, I get the error that Global symbol "$widx" requires explicit package name at getattach.pl line 131., which is because instead of $wid and x seperately, the compiler sees $widx as a new undeclared variable.

I tried inserting double quotes inside the backticks, but execution of code stopped without any messages.

What's the proper way of inserting variable names in backticks for shell execution? Can they be concatenated?

like image 862
Joel G Mathew Avatar asked Jun 09 '13 12:06

Joel G Mathew


People also ask

How do I assign a variable in Perl?

Perl variables do not have to be explicitly declared to reserve memory space. The declaration happens automatically when you assign a value to a variable. The equal sign (=) is used to assign values to variables.

What is $@ in Perl?

$@ The Perl syntax error or routine error message from the last eval, do-FILE, or require command. If set, either the compilation failed, or the die function was executed within the code of the eval.

Which of the following is valid variable name in Perl?

Perl scalar variables are prefixed by the dollar sign ($) character. In addition, all Perl variable names must follow these rules: Variable names must contain only letters (a-z, A-Z), underscores (_), and numeric digits (0-9). The first character of a variable name must be a letter (a-z, A-Z) or underscore (_).

What is the meaning of $_ in Perl?

The most commonly used special variable is $_, which contains the default input and pattern-searching string. For example, in the following lines − #!/usr/bin/perl foreach ('hickory','dickory','doc') { print $_; print "\n"; }


1 Answers

To insert a variable into any interpolating string (be it qq// or qx or qr//), just doing "this is $foo!" is sufficient: The variable name (here: $foo) is delimited by the ! which cannot be part of a normal variable name.

It is not so easy when parts of the string could be part of the name by Perl's naming rules. Example:

my $genes = "ACTG$insert_genes_hereACTG";

Perl considers the variable name to be $insert_genes_hereACTG. This can be solved by

  1. Using curlies to delimit the name:

    my $genes = "ACTG${insert_genes_here}ACTG";
    

    This always works and is a flexible solution

  2. Concatenating the string:

    my $genes = "ACTG" . $insert_genes_here . "ACTG";
    

    This is a bit difficult for non-qq-quotes. A solution is to create a temporary variable that holds the whole string, and then interpolates it into special quotes:

    my $command = "mogrify -resize " . $wid . "x" . $hit. " *JPG";
    `$command`;
    

    A variant of this is to use sprintf interpolation:

    my $command = sprintf 'mogrify -resize %dx%d *JPG', $wid, $hit;
    

As an aside, many shell interpolation problems can be circumvented by not using backticks, and using open or system instead (depending on whether or not you need output).

With open:

open my $command, "-|", "mogrify", "-resize", $wid . "x" . $hit, glob("*JPG")
  or die ...;

while (<$command>) { do something }

This completely circumvents the shell (and rather execs directly), so globbing has to be done manually. The same holds true for system with more than one argument.

like image 194
amon Avatar answered Sep 21 '22 17:09

amon