2010-09-15 14 views
5

Por alguna razón, no puedo hacer que Filehandles funcione con el método log_file de Expect.pm. Originalmente recibí ayuda en How can I pass a filehandle to Perl Expect's log_file function?, donde se me sugirió que use un identificador de archivo IO :: Handle para pasar al método. Este parece ser un problema diferente, así que pensé en comenzar una nueva pregunta.¿Por qué mi identificador de archivo bendecido de Perl no devuelve verdadero con `can ('print')` '?

Ésta es la sección del infractor Expect.pm:

if (ref($file) ne 'CODE') { 
    croak "Given logfile doesn't have a 'print' method" 
    if not $fh->can("print"); 
    $fh->autoflush(1);  # so logfile is up to date 
} 

Así, pues, he intentado este código de ejemplo:

use IO::Handle; 
open $fh, ">>", "file.out" or die "Can't open file"; 
$fh->print("Hello, world"); 
if ($fh->can("print")) 
{ 
    print "Yes\n"; 
} 
else 
{ 
    print "No\n"; 
} 

Cuando ejecuto esto, y llévese dos (a mi mente) artículos en conflicto Un archivo con una sola línea que dice "Hola, mundo", y una salida de "No". En mi opinión, la línea $fh->can debería ser verdadera. ¿Me equivoco aquí?

+2

'use strict; usar advertencias; ' – Ether

+0

No tengo una respuesta sobre por qué esto está actuando raro, pero sospecho que parte de esto proviene de IO :: Handle no es una clase normal. Algo de eso está dentro de la fuente perl en lugar de vivir como un módulo normal. Podría merecer un informe de error (use perlbug) :) –

Respuesta

5

Extraño, parece que necesita crear un objeto real IO::File para que el método can funcione. Pruebe

use IO::File; 

my $fh = IO::File->new("file.out", ">>") 
    or die "Couldn't open file: $!"; 
+0

IO :: File usado. Gracias una vez más por tu ayuda. –

2

IO::Handle no sobrecarga la función open(), por lo que no está consiguiendo realmente un objeto IO::Handle en $fh. No sé por qué funciona la línea $fh->print("Hello, world") (probablemente porque está llamando a la función print(), y cuando hace cosas como $foo->function es equivalente a function $foo, por lo que básicamente está imprimiendo en el manejador de archivos como lo esperaría normalmente).

Si cambia el código a algo como:

use strict; 
use IO::Handle; 
open my $fh, ">>", "file.out" or die "Can't open file"; 
my $iofh = new IO::Handle; 
$iofh->fdopen($fh, "w"); 
$iofh->print("Hello, world"); 
if ($iofh->can("print")) 
{ 
    print "Yes\n"; 
} 
else 
{ 
    print "No\n"; 
} 

... entonces su código hará lo que usted espera. ¡Por lo menos lo hace por mí!

+0

¿Por qué estás usando 'abrir' +' fdopen' en lugar de simplemente usar 'IO :: File'? – cjm

+0

Porque no sabía acerca de 'IO :: File' hasta que vi la respuesta de Chas. Tenía 'IO :: Handle' en el cerebro porque eso es lo que pensé que el OP quería usar. – CanSpice

+0

Tampoco sabía acerca de IO :: File hasta que lo busqué en este momento. ¡Gracias por tu ayuda una vez más! Siempre una experiencia de aprendizaje. –

Cuestiones relacionadas