Liệt kê các tệp đệ quy trong Linux CLI với đường dẫn liên quan đến thư mục hiện tại


224

Điều này tương tự với câu hỏi này , nhưng tôi muốn bao gồm đường dẫn liên quan đến thư mục hiện tại trong unix. Nếu tôi làm như sau:

ls -LR | grep .txt

Nó không bao gồm các đường dẫn đầy đủ. Ví dụ, tôi có cấu trúc thư mục sau:

test1/file.txt
test2/file1.txt
test2/file2.txt

Mã ở trên sẽ trả về:

file.txt
file1.txt
file2.txt

Làm thế nào tôi có thể làm cho nó bao gồm các đường dẫn liên quan đến thư mục hiện tại bằng cách sử dụng các lệnh Unix tiêu chuẩn?


4
Điều này chỉ cho thấy rằng ls đang thiếu tính năng này.
Arjun Singri

1
Thật xấu hổ khi tất cả các giải pháp này yêu cầu findhoặc tree. Tôi đang tham gia vào một thiết bị Android mà tôi dường như chỉ có lsvà không có công cụ nào trong số này: /
Ponkadoodle

Câu trả lời:


304

Sử dụng tìm:

find . -name \*.txt -print

Trên các hệ thống sử dụng GNU find, giống như hầu hết các bản phân phối GNU / Linux, bạn có thể bỏ qua phần in.


11
... và đối với vấn đề đó, bạn có thể bỏ qua '.'
Adam Mitz

7
Đối với đường dẫn tuyệt đối, sử dụngfind $(pwd) -name \*.txt
Zags

2
Nếu mẫu có một phần của tên thư mục nên sử dụng -path "*docs/*.txt"thay vì -name. -wholenamecũng giống như-path
bảnh bao

9
Sử dụng -type fđể chỉ trả lại các tệp và không phải thư mục, liên kết tượng trưng, ​​v.v.
người dùng

2
-name "*.txt"sẽ KHÔNG khớp file.TXT- luôn luôn sử dụng -iname "*.txt"thay cho trường hợp không phân biệt chữ hoa chữ thường.
ccpizza

73

Sử dụng tree, với -f(đường dẫn đầy đủ) và -i(không có dòng thụt):

tree -if --noreport .
tree -if --noreport directory/

Sau đó, bạn có thể sử dụng grepđể lọc ra những cái bạn muốn.


Nếu không tìm thấy lệnh, bạn có thể cài đặt nó:

Gõ lệnh sau để cài đặt lệnh cây trên RHEL / CentOS và Fedora linux:

# yum install tree -y

Nếu bạn đang sử dụng Debian / Ubuntu, Mint Linux gõ lệnh sau trong thiết bị đầu cuối của bạn:

$ sudo apt-get install tree -y

2
bất kỳ cài đặt nào chỉ liệt kê các tệp và loại trừ các thư mục?
Bọ rùa

25

Hãy thử find. Bạn có thể tra cứu chính xác trong trang người đàn ông, nhưng nó giống như thế này:

find [start directory] -name [what to find]

ví dụ của bạn

find . -name "*.txt"

sẽ cung cấp cho bạn những gì bạn muốn.



5

Đó là mẹo:

ls -R1 $PWD | while read l; do case $l in *:) d=${l%:};; "") d=;; *) echo "$d/$l";; esac; done | grep -i ".txt"

Nhưng nó thực hiện điều đó bằng cách "phạm tội" với việc phân tích cú pháp ls, mặc dù, được coi là hình thức xấu của cộng đồng GNU và Ghostscript.


2
@CAFEBABE: nó được coi là điều cấm kỵ khi phân tích kết quả lsvì nó thường dẫn đến lỗi. Câu trong câu hỏi đã cố gắng để gọi nó ra. Nó cũng có một trò đùa trong đó mà tôi đã loại bỏ.
Adam Katz

4
DIR=your_path
find $DIR | sed 's:""$DIR""::'

'sed' sẽ xóa 'your_path' khỏi tất cả các kết quả 'tìm'. Và bạn nhận được liên quan đến đường dẫn 'TRỰC TIẾP'.


đây chính xác là những gì tôi cần nhưng nó vẫn tạo ra con đường đầy đủ cho tôi?
v3nt

1
không sử dụng dấu nháy đơn - find / tmp | sed s: "/ tmp" :: | thêm
Kieren Dixon

4

Để có được tên tệp đường dẫn đầy đủ thực tế của các tệp mong muốn bằng lệnh find, hãy sử dụng nó với lệnh pwd:

find $(pwd) -name \*.txt -print

1

Đây là một kịch bản Perl:

sub format_lines($)
{
    my $refonlines = shift;
    my @lines = @{$refonlines};
    my $tmppath = "-";

    foreach (@lines)
    {
        next if ($_ =~ /^\s+/);
        if ($_ =~ /(^\w+(\/\w*)*):/)
        {
            $tmppath = $1 if defined $1;    
            next;
        }
        print "$tmppath/$_";
    }
}

sub main()
{
        my @lines = ();

    while (<>) 
    {
        push (@lines, $_);
    }
    format_lines(\@lines);
}

main();

sử dụng:

ls -LR | perl format_ls-LR.pl

Đây là một chương trình Perl khủng khiếp. Nó có thể dài gấp 2-3 lần và phức tạp hơn mức cần thiết.
Brad Gilbert

1

Bạn có thể tạo một hàm shell, ví dụ như trong .zshrchoặc .bashrc:

filepath() {
    echo $PWD/$1
}

filepath2() {
    for i in $@; do
        echo $PWD/$i
    done
}

Rõ ràng là cái đầu tiên chỉ hoạt động trên các tệp duy nhất.


1

Tìm tệp có tên "tên tệp" trên hệ thống tệp của bạn bắt đầu tìm kiếm từ thư mục gốc "/". "Tên tệp"

find / -name "filename" 

1

Nếu bạn muốn giữ các chi tiết đi kèm với ls như kích thước tệp, v.v. trong đầu ra của bạn thì điều này sẽ hoạt động.

sed "s|<OLDPATH>|<NEWPATH>|g" input_file > output_file

1

Trong vỏ , bạn có thể làm điều này để liệt kê tất cả các tệp pdf theo cách đệ quy, bao gồm cả các tệp trong thư mục hiện tại:

$ ls **pdf

Chỉ cần xóa 'pdf' nếu bạn muốn các loại tệp.


0

Bạn có thể thực hiện chức năng này như thế này
Trước tiên, sử dụng lệnh ls được trỏ đến thư mục được nhắm mục tiêu. Sau này sử dụng bộ lọc lệnh find kết quả từ nó. Từ trường hợp của bạn, có vẻ như - luôn luôn tên tệp bắt đầu bằng một từ file***.txt

ls /some/path/here | find . -name 'file*.txt'   (* represents some wild card search)

0

Trong mycase, với lệnh cây

Đường dẫn tương đối

tree -ifF ./dir | grep -v '^./dir$' | grep -v '.*/$' | grep '\./.*' | while read file; do
  echo $file
done

Con đường tuyệt đối

tree -ifF ./dir | grep -v '^./dir$' | grep -v '.*/$' | grep '\./.*' | while read file; do
  echo $file | sed -e "s|^.|$PWD|g"
done
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.