3

I have an object with a method that returns a filehandle, and I want to read from that handle. The following doesn't work, because the right angle bracket of the method call is interpreted as the closing angle bracket of the input reader:

my $input = <$object->get_handle()>;

That gets parsed as:

my $input = ( < $object- > ) get_handle() >;

which is obviously a syntax error. Is there any way I can perform a method call within an angle operator, or do I need to break it into two steps like this?

my $handle = $object->get_handle();
my $input = <$handle>;
brian d foy
  • 129,424
  • 31
  • 207
  • 592
Ryan C. Thompson
  • 40,856
  • 28
  • 97
  • 159

4 Answers4

7

You could consider spelling <...> as readline(...) instead, which avoids the problem by using a nice regular syntax instead of a special case. Or you can just assign it to a scalar. Your choice.

hobbs
  • 223,387
  • 19
  • 210
  • 288
3

You have to break it up; the <> operator expects a typeglob like <STDIN>, a simple scalar variable containing a reference to a filehandle or typeglob like <$fh>, or an argument for the glob() function like <*.c>. In your example, you're actually calling glob('$object-').

<> is actually interpreted as a call to readline(), so if you really want to you could say my $input = readline( $object->get_handle() ); I'm not sure that's cleaner though, especially if you're going to read from the handle more than once.

See http://perldoc.perl.org/perlop.html#I%2fO-Operators for details.

DougWebb
  • 680
  • 5
  • 11
1
my $input = readline($object->get_handle());

or

use IO::Handle;

my $input = $object->get_handle()->getline();
0

You won't be able to use the <...> operator here to read a file handle, because anything more complex than <bareword> or <$scalar> is interpreted as a glob(...) call, so none of the usual disambiguation tricks will work here. The <HANDLE> operator is syntactic sugar for readline HANDLE, so you could write it this way:

my $input = readline $object->get_handle;

However, if you will be doing this in a loop, it will be far more efficient to cache the handle in a scalar. Then the <...> operator will work as you expected:

my $handle = $object->get_handle;
while (my $input = <$handle>) {
    ...
}
Eric Strom
  • 39,821
  • 2
  • 80
  • 152
  • I'd prefer not to use indirect object syntax. It's fragile. I'd have to commit to never allowing my code to come anywhere near a `get_handle` subroutine. – Ryan C. Thompson Apr 20 '10 at 02:54
  • @Ryan: If you're not concerned about this problem from a purely academic perspective, I'd go with the two statement solution that you provided in the question. Syntactically however, it looks like Eric's solution could work. It would look nice in Perl poetry. – Ether Apr 20 '10 at 02:59
  • 1
    `readline FILE` is the exact same thing as ``, so that would work fine. – Brian Roach Apr 20 '10 at 03:04