hide random home http://www.fmi.uni-passau.de/archive/doc/unix/perl/faq/2.1.html (Einblicke ins Internet, 10/1995)

What are all these $@*%<> signs and how do I know when to use them?

What are all these $@*%<> signs and how do I know when to use them?


    Those are type specifiers: $ for scalar values, @ for indexed arrays,
    and % for hashed arrays.  The * means all types of that symbol name
    and are sometimes used like pointers; the <> are used for inputting
    a record from a filehandle.  See the question on arrays of arrays
    for more about Perl pointers.

    Always make sure to use a $ for single values and @ for multiple ones.
    Thus element 2 of the @foo array is accessed as $foo[2], not @foo[2],
    which is a list of length one (not a scalar), and is a fairly common
    novice mistake.  Sometimes you can get by with @foo[2], but it's
    not really doing what you think it's doing for the reason you think
    it's doing it, which means one of these days, you'll shoot yourself
    in the foot; ponder for a moment what these will really do:
        @foo[0] = `cmd args`;
        @foo[2] = <FILE>;
    Just always say $foo[2] and you'll be happier.

    This may seem confusing, but try to think of it this way:  you use the
    character of the type which you *want back*.  You could use @foo[1..3] for
    a slice of three elements of @foo, or even @foo{A,B,C} for a slice of
    of %foo.  This is the same as using ($foo[1], $foo[2], $foo[3]) and
    ($foo{A}, $foo{B}, $foo{C}) respectively.  In fact, you can even use
    lists to subscript arrays and pull out more lists, like @foo[@bar] or
    @foo{@bar}, where @bar is in both cases presumably a list of subscripts.

    While there are a few places where you don't actually need these type
    specifiers, except for files, you should always use them.  Note that
    <FILE> is NOT the type specifier for files; it's the equivalent of awk's
    getline function, that is, it reads a line from the handle FILE.  When
    doing open, close, and other operations besides the getline function on
    files, do NOT use the brackets.

    Beware of saying:
        $foo = BAR;
    Which wil be interpreted as 
        $foo = 'BAR';
    and not as 
        $foo = <BAR>;
    If you always quote your strings, you'll avoid this trap.

    Normally, files are manipulated something like this (with appropriate
    error checking added if it were production code):

        open (FILE, ">/tmp/foo.$$");
        print FILE "string\n";
        close FILE;

    If instead of a filehandle, you use a normal scalar variable with file
    manipulation functions, this is considered an indirect reference to a
    filehandle.  For example,

        $foo = "TEST01";
        open($foo, "file");

    After the open, these two while loops are equivalent:

        while (<$foo>) {}
        while (<TEST01>) {}

    as are these two statements:
        
        close $foo;
        close TEST01;

    but NOT to this:

        while (<$TEST01>) {} # error
                ^
                ^ note spurious dollar sign

    This is another common novice mistake; often it's assumed that

        open($foo, "output.$$");

    will fill in the value of $foo, which was previously undefined.  
    This just isn't so -- you must set $foo to be the name of a valid
    filehandle before you attempt to open it.