web-dev-qa-db-fra.com

Comment puis-je vérifier si un descripteur de fichier est ouvert dans Perl?

Existe-t-il un moyen de vérifier si un fichier est déjà ouvert dans Perl? Je veux avoir un accès en lecture de fichier, donc pas besoin de flock.

 open(FH, "<$fileName") or die "$!\n" if (<FILE_IS_NOT_ALREADY_OPEN>);
 #  or something like
 close(FH) if (<FILE_IS_OPEN>);
31
matt

Veuillez consulter la réponse concernant openhandle() à partir de Scalar::Util . La réponse que j’avais écrite à l’origine était autrefois ce que nous pouvions faire de mieux, mais elle est maintenant extrêmement dépassée.

38
chaos

Le module Scalar :: Util fournit la fonction openhandle() pour cela. Contrairement à fileno () , il gère les descripteurs de fichiers Perl non associés aux descripteurs de fichiers du système d'exploitation. Contrairement à tell () , il ne produit pas d'avertissement lorsqu'il est utilisé sur un descripteur de fichier non ouvert. Du documentation du module: 

poignée ouverte FH

Returns FH if FH may be used as a filehandle and is open, or FH is a tied handle. Otherwise "undef" is returned.

   $fh = openhandle(*STDIN);           # \*STDIN
   $fh = openhandle(\*STDIN);          # \*STDIN
   $fh = openhandle(*NOTOPEN);         # undef
   $fh = openhandle("scalar");         # undef
22
brady

Pourquoi voudriez-vous faire ça? La seule raison pour laquelle je peux penser est que vous utilisez des poignées de fichier de paquet de style ancien (ce que vous semblez être en train de faire) et que vous voulez éviter d'enregistrer accidentellement une poignée sur une autre.

Ce problème peut être résolu en utilisant de nouveaux descripteurs de fichiers indirects de style.

open my $fh, '<', $filename or die "Couldn't open $filename: $!";
12
Leon Timmermans

Perl fournit la fonction fileno dans ce but précis.

EDIT Je reste corrigé sur le but de fileno(). Je préfère le test plus court

fileno FILEHANDLE

plus de

tell FH != -1

8
converter42

Tell produit un avertissement (de même que stat, -s, -e, etc.) avec use warnings (-w)

Perl -wle '
    open my $fh, "<", "notexists.txt"; 
    print "can stat fh" if tell $fh
'
tell() on closed filehandle $fh at -e line 1.
-1

Les alternatives fileno($fh) et eof($fh) ne produisent pas d'avertissements. J'ai trouvé que la meilleure solution consistait à enregistrer le résultat de open.

1
CoffeeMonster

Pourquoi vous souciez-vous s'il est déjà ouvert? Essayez-vous d’attraper des lectures simultanées?

Vous n'avez pas vraiment besoin de vous soucier de la fermeture du fichier. Soit il n’est pas ouvert et la fermeture échoue car il n’a rien à fermer, ou le fichier est ouvert et la fermeture le libère. Dans les deux cas, le fichier n'est pas ouvert sur ce descripteur de fichier. Fermez simplement le descripteur de fichier sans vous en soucier s'il n'est pas ouvert. Voyez-vous quelque chose de bizarre là-bas?

0
brian d foy