2009-09-25 38 views
48

Tôi cần phải kiểm tra xem một tập tin trong thư mục chính của người dùng tồn tại để sử dụng kiểm tra file:Làm cách nào để tìm thư mục chính của người dùng trong Perl?

if (-e "~/foo.txt") { 
    print "yes, it exists!" ; 
} 

Mặc dù có một tập tin gọi là foo.txt dưới thư mục chính của người dùng, Perl luôn phàn nàn rằng không có tệp hoặc thư mục nào như vậy. Khi tôi thay thế "~" bằng /home/jimmy (giả sử người dùng là jimmy) thì Perl đưa ra phán quyết đúng.

Bạn có thể giải thích lý do tại sao "~" không hoạt động trong Perl và cho tôi biết cách của Perl là tìm thư mục chính của người dùng là gì?

+17

~ là một điều vỏ. Đó là lý do tại sao nó không hoạt động trong Perl. :) –

Trả lời

63

~ là một bash-chủ nghĩa hơn là một perl -ism, đó là lý do tại sao nó không hoạt động. Cho rằng bạn dường như là trên một hệ thống UNIX-type, có lẽ là giải pháp dễ nhất là sử dụng biến $HOME môi trường, chẳng hạn như:

if (-e $ENV{"HOME"} . "/foo.txt") { 
    print "yes ,it exists!" ; 
} 

Và vâng, tôi biết người dùng có thể thay đổi biến $HOME môi trường xung quanh nhưng sau đó tôi cho rằng họ biết họ đang làm gì. Nếu không, họ xứng đáng với mọi thứ họ nhận được :-)

Nếu bạn muốn thực hiện theo cách bên phải, bạn có thể xem File::HomeDir, hiểu biết nhiều hơn về nền tảng. Bạn có thể nhìn thấy nó trong hành động trong kịch bản sau đây chkfile.pl:

use File::HomeDir; 
$fileSpec = File::HomeDir->my_home . "/foo.txt"; 
if (-e $fileSpec) { 
    print "Yes, it exists!\n"; 
} else { 
    print "No, it doesn't!\n"; 
} 

và bảng điểm:

 
pax$ touch ~/foo.txt ; perl chkfile.pl 
Yes, it exists! 

pax$ rm -rf ~/foo.txt ; perl chkfile.pl 
No, it doesn't! 
+10

Có một vài vấn đề với điều này: không phải tất cả các phiên đều có HOME được đặt và không phải mọi hệ thống đều xây dựng đường dẫn của chúng như unix. File :: HomeDir sẽ cung cấp cho bạn câu trả lời đúng. –

+8

Không bao giờ giả sử khi bạn không cần. Các chương trình hữu ích có xu hướng di chuyển.:) –

+0

Đáp _really_ trả lời muộn này, nhưng nó có thể hữu ích cho người đọc hiện tại - một cách khác là sử dụng 'glob ('~/foo.txt')'. Điều này có lợi thế là nó sẽ mở rộng đúng cách những thứ như '~ user123/foo.txt'. Tôi nhận ra OP đặc biệt đề cập đến thư mục nhà, nhưng tôi đã xem xét điều này khi tìm kiếm một cái gì đó chung chung hơn, và nghĩ rằng tôi sẽ giúp những người khác theo cùng một con đường. – John

11

Các thư mục home cho người dùng được lưu trữ trong /etc/passwd. Cách tốt nhất để có được thông tin là getpw* functions:

#!/usr/bin/perl 

use strict; 
use warnings; 

print "uid:", (getpwuid 501)[7], "\n", 
    "name:", (getpwnam "cowens")[7], "\n"; 

Để giải quyết vấn đề cụ thể của bạn, hãy thử mã này:

if (-e (getpwuid $>)[7] . "/foo.txt") { 
    print "yes ,it exists!"; 
} 
+1

Tệp :: HomeDir không phải là một mô-đun lõi, vì vậy đây có thể là một lựa chọn tốt nếu bạn không muốn thêm phụ thuộc. – CoverosGene

14

Bạn có thể glob dấu ngã, glob('~/foo.txt') nên làm việc. Hoặc bạn có thể sử dụng mô-đun File::Save::Home cũng nên quản lý các hệ thống khác.

+6

Tại sao lại là downvote? Cả hai cách tiếp cận đều hoạt động. Nếu có vấn đề với họ, tôi muốn biết. – zoul

+0

Xin chào Tôi chỉ là người mới bắt đầu nhưng nếu tôi có một .jpg trong thư mục nhà Win 7 của tôi và tôi chạy: print glob ('~/*. Jpg'); nó không làm gì cả. nhưng nếu tôi chạy: in glob ('Users/Daniel/*. jpg'); nó in: /Users/Daniel/JanesJinormousJugs.jpg – Literat

+0

Giải pháp không di động rất thanh lịch. Nếu bạn có một kịch bản perl được viết để chạy cụ thể trong môi trường Linux (ví dụ: bạn bẻ khóa các tập lệnh bash, thì bạn sẽ không mất bất cứ thứ gì bằng cách làm theo cách này, vì bạn đã không di động) –

56

Tôi không chắc chắn cách mọi người bỏ lỡ File::HomeDir. Đó là một trong những nhiệm vụ khó nghe dễ dàng bởi vì không ai biết về tất cả các ngoại lệ ngốc nghếch mà bạn phải suy nghĩ. Nó không đi kèm với Perl, vì vậy bạn cần phải cài đặt nó cho mình.

Một khi bạn biết các thư mục chính, xây dựng con đường mà bạn cần với File::Spec:

use File::HomeDir qw(home); 
use File::Spec::Functions qw(catfile); 

print "The path is ", catfile(home(), 'foo.txt'), "\n"; 
+0

hoặc sử dụng với 'File :: chdir' (mô-đun CPAN fav của tôi):' ... sử dụng File :: chdir; {local $ CWD = home; nếu (-e $ file) {...}} ', nền tảng độc lập, chặn quản lý thư mục làm việc cục bộ! –

Các vấn đề liên quan