2009-05-08 11 views

risposta

56

EDIT: Mettere la soluzione giusta prima, originariamente da this question. E 'l'unico che cerca relativo alla directory del modulo :

use FindBin;     # locate this script 
use lib "$FindBin::Bin/.."; # use the parent directory 
use yourlib; 

Ci sono molti altri modi in cui cercare le librerie relativi alla directory corrente . È possibile richiamare perl con l'argomento -I, passando la directory dell'altro modulo:

perl -I.. yourscript.pl 

È possibile includere una linea vicino alla parte superiore dello script perl:

use lib '..'; 

È possibile modificare l'ambiente PERL5LIB variabile prima di eseguire lo script:

export PERL5LIB=$PERL5LIB:.. 

l'(@INC) strategia di spinta può anche funzionare, ma deve essere avvolto in BEGIN {} per assicurarsi che la spinta viene eseguito prima che il modulo di ricerca sul sito h:

+0

Dopo molti tentativi il codice che ha funzionato alla fine è stato dalla domanda che Andomar ha collegato a: utilizzare FindBin; # trova questo scriptuse lib "$ FindBin :: Bin/.."; # usa la directory principale usa EPMS; Grazie per tutto il vostro aiuto a tutti! –

+0

Cheers, sembra che tutti leggano "directory corrente" dove hai scritto "directory del modulo". – Andomar

+0

È venuto fuori dopo aver letto http://stackoverflow.com/a/90721/2668831 che afferma che il metodo FindBin non è affidabile per alcune forme di organizzazione Perl modulare (qualcun altro potrebbe essere in grado di chiarire) –

10

'uso lib' può anche prendere un singolo valore stringa ...

#!/usr/bin/perl 
use lib '<relative-path>'; 
use <your lib>; 
+0

Qual è il relativo percorso relativo? – Flimm

12

Molto probabilmente il motivo per cui la tua spinta non ha funzionato è l'ordine di esecuzione.

use è una direttiva di compilazione. È push è fatto a tempo di esecuzione:

push (@INC,"directory_path/more_path"); 
use Foo.pm; # In directory path/more_path 

È possibile utilizzare un blocco BEGIN per aggirare questo problema:

BEGIN { 
    push (@INC,"directory_path/more_path"); 
} 
use Foo.pm; # In directory path/more_path 

IMO, è chiaro, e quindi meglio use lib:

use lib "directory_path/more_path"; 
use Foo.pm; # In directory path/more_path 

Vedere perlmod per informazioni su BEGIN e altri blocchi speciali e quando vengono eseguiti.

Modifica

Per il codice di carico relativa allo script/biblioteca, sottoscrivo fortemente File::FindLib

Si può dire use File::FindLib 'my/test/libs'; per cercare una directory di libreria ovunque sopra lo script nel percorso.

Dite il vostro lavoro è strutturato in questo modo:

/home/me/projects/ 
    |- shared/ 
    | |- bin/ 
    | `- lib/ 
    `- ossum-thing/ 
     `- scripts 
      |- bin/ 
      `- lib/ 

all'interno di uno script in ossum-thing/scripts/bin:

use File::FindLib 'lib/'; 
use File::FindLib 'shared/lib/'; 

troverete la vostra directory di libreria e aggiungerli al tuo @INC.

È anche utile creare un modulo che contenga tutte le impostazioni dell'ambiente necessarie per eseguire la suite di strumenti e caricarlo in tutti gli eseguibili del progetto.

use File::FindLib 'lib/MyEnvironment.pm' 
7

Da perlfaq8:


Come si aggiunge la directory mio programma vive dentro al/libreria percorso di ricerca del modulo?

(contributo di brian d foy)

Se si conosce già la directory, è possibile aggiungerlo a @INC come si farebbe per qualsiasi altra directory. È possibile utilizzare lib se si conosce la directory in fase di compilazione:

use lib $directory; 

Il trucco in questo compito è trovare la directory. Prima che il vostro script fa qualsiasi altra cosa (come un chdir), è possibile ottenere la directory corrente di lavoro con il modulo Cwd, che viene fornito con il Perl:

BEGIN { 
    use Cwd; 
    our $directory = cwd; 
    } 

use lib $directory; 

Si può fare una cosa simile con il valore di $ 0, che detiene il nome dello script. Questo potrebbe contenere un percorso relativo, ma rel2abs può trasformarlo in un percorso assoluto. Una volta che hai il

BEGIN { 
    use File::Spec::Functions qw(rel2abs); 
    use File::Basename qw(dirname); 

    my $path = rel2abs($0); 
    our $directory = dirname($path); 
    } 

use lib $directory; 

Il modulo FindBin, fornito con Perl, potrebbe funzionare. Essa trova la directory dello script attualmente in esecuzione e lo mette in $ Bin, che è possibile utilizzare per costruire il percorso della libreria destra:

use FindBin qw($Bin); 
+0

Il tuo secondo suggerimento (usando 'cwd' all'interno di un blocco 'BEGIN') non sembra funzionare. Tutto ciò che ottengo è il seguente errore: 'Variabile" $ directory "non viene importato in ./thingy line 16. // Il simbolo globale" $ directory "richiede il nome del pacchetto esplicito alla riga ./thingy 16. // BEGIN non sicuro dopo gli errori - la compilazione è stata interrotta all'indirizzo ./thingy line 16. – zrajm

+0

Dovresti mostrarmi il tuo codice. Sembra che tu abbia citato $ directory nella lista di importazione. –

0

Mi sorprende che nessuno ha parlato prima, ma FindBin::libs troverà sempre le tue librerie mentre cerca in tutti i posti ragionevoli relativi alla posizione del tuo script.

#!/usr/bin/perl 
use FindBin::libs; 
use <your lib>; 
0

Ti dirò come può essere fatto in eclissi. Il mio sistema di sviluppo - Windows 64bit, Eclipse Luna, plugin Perlipse per eclipse, installazione Strawberry Pearl. Io uso perl.exe come mio interprete.

Eclipse> crea un nuovo progetto perl> fai clic con il tasto destro del mouse sul progetto> crea percorso> configura percorso di compilazione> scheda librerie> aggiungi cartella di origine esterna> vai alla cartella in cui sono installati tutti i moduli perl> ok> ok. Fatto !

Problemi correlati