Làm thế nào để tìm một tập tin trong hệ thống tập tin từ dòng lệnh?


10

Tôi muốn tìm vị trí của một tệp (với tên tệp được biết một phần) trong hệ thống tệp. Tôi muốn biết cách thực hiện điều này từ dòng lệnh, thay vì sử dụng tiện ích GUI.

Trong Windows, tôi sẽ chạy như sau:

cd /d C:\
dir *filename* /s

Linux tương đương là gì?


Chà, rõ ràng có nhiều hơn một cách để lột da con mèo này . Tôi vẫn còn một chút tò mò muốn biết liệu có cách nào để làm điều đó lskhông?
Iszi

Câu trả lời:


13
locate filename
find -name '*filename*'
echo **/*filename*
ls -ld **/*filename*

(Đọc về các điều khoản và điều kiện chính. Đọc hướng dẫn cho bản in đẹp.)

Liệt kê nội dung của một thư mục là một tính năng phụ của ls. Công việc chính của ls, công việc chiếm phần lớn sự phức tạp của nó, là tinh chỉnh màn hình của nó. (Xem hướng dẫn và so sánh số lượng tùy chọn liên quan đến việc chọn tệp nào sẽ hiển thị so với số tùy chọn kiểm soát thông tin nào sẽ hiển thị về mỗi tệp và cách hiển thị được định dạng. Đây là sự thật của cả GNU và bạn. sẽ tìm thấy trên Linux và các hệ thống khác có ít tùy chọn hơn, kể từ những ngày đầu .)

Chế độ mặc định lslà khi bạn truyền cho nó một thư mục, nó sẽ liệt kê các tệp trong thư mục đó. Nếu bạn chuyển cho nó bất kỳ loại tệp nào khác (tệp thông thường, liên kết tượng trưng, ​​v.v.), thì nó chỉ liệt kê tệp đó. (Điều này áp dụng riêng cho từng đối số.) Tùy chọn -dcho biết lskhông bao giờ đi vào một thư mục.

lskhông có một tùy chọn -Rcho biết nó liệt kê các thư mục đệ quy. Nhưng đó là khả năng ứng dụng hạn chế và không cho phép lọc nhiều đầu ra.

Công cụ đầu tiên để thực hiện khớp mẫu là chính vỏ. Bạn không cần bất kỳ lệnh nào khác: chỉ cần nhập ký tự đại diện của bạn và bạn đã thiết lập. Điều này được gọi là Globing .

echo *filename*

Theo truyền thống, ký tự đại diện được giới hạn trong thư mục hiện tại (hoặc thư mục được chỉ định echo /some/where/*filename*:). A *khớp với bất kỳ tên tệp nào, hoặc bất kỳ phần nào của tên tệp, nhưng *.txtsẽ không khớp foo/bar.txt. Các shell hiện đại đã thêm mô hình **/có nghĩa là trong thư mục này hoặc trong bất kỳ thư mục nào bên dưới nó (đệ quy). Với bash, vì lý do tương thích lịch sử, tính năng này cần được kích hoạt rõ ràng shopt -s globstar(bạn có thể đặt dòng này trong ~/.bashrc).

echo **/*filename*

Các echolệnh chỉ vang danh sách các tên tập tin được tạo ra bởi mặt sau vỏ vào bạn. Như một ngoại lệ, nếu hoàn toàn không có tên tệp phù hợp, mẫu ký tự đại diện sẽ không thay đổi trong bash (trừ khi bạn đặt shopt -s nullglob, trong trường hợp đó, mẫu sẽ mở rộng thành một danh sách trống) và zsh báo lỗi (trừ khi bạn đặt setopt nullglob, hoặc setopt no_no_matchmà làm cho mô hình được để lại không thay đổi).

Bạn vẫn có thể muốn sử dụng lscho các tùy chọn của nó. Ví dụ: lscó thể đưa ra các chỉ dẫn về bản chất hoặc quyền của tệp (thư mục, tệp thực thi, v.v.) thông qua màu sắc. Bạn có thể muốn hiển thị ngày, kích thước và quyền sở hữu của tệp ls -l. Xem hướng dẫn để biết thêm nhiều lựa chọn.

Lệnh truyền thống để tìm tệp trong cây thư mục là find. Nó đi kèm với nhiều tùy chọn để kiểm soát tập tin nào sẽ hiển thị và phải làm gì với chúng. Ví dụ: để tìm các tệp có tên khớp với mẫu *filename*trong thư mục hiện tại và các thư mục con của nó và in tên của chúng:

find /some/dir -name '*filename*' -print

-printlà một hành động (hầu hết các hành động khác bao gồm thực thi một lệnh trên tệp); nếu bạn không đặt một hành động, -printđược ngụ ý. Ngoài ra, nếu bạn không chỉ định bất kỳ thư mục nào đi qua ( /some/dirở trên), thư mục hiện tại được ngụ ý. Điều kiện -name '*filename'nói chỉ liệt kê (hoặc hành động) các tệp có tên khớp với mẫu đó; có nhiều bộ lọc khác, chẳng hạn như -mtime -1để khớp với các tệp được sửa đổi trong 24 giờ qua. Đôi khi bạn có thể bỏ qua các trích dẫn trên -name '*filename*', nhưng chỉ khi ký tự đại diện không khớp với bất kỳ tệp nào trong thư mục hiện tại (xem bên trên). Tất cả trong tất cả, hình thức ngắn là

find -name '*filename*'

Một công cụ hữu ích khác khi bạn biết (một phần) tên của tệp là locate. Công cụ này truy vấn cơ sở dữ liệu về tên tệp. Trên các hệ thống điển hình, nó được làm mới mỗi đêm. Ưu điểm của việc locatetrên find /là nó nhanh hơn rất nhiều. Một nhược điểm là thông tin của nó có thể cũ. Có một số cách triển khai locatekhác nhau trong hành vi của họ trên các hệ thống nhiều người dùng: các locatechương trình cơ bản chỉ lập các tệp có thể đọc công khai (bạn có thể muốn chạy đồng hành updatedbđể tạo cơ sở dữ liệu thứ hai lập chỉ mục tất cả các tệp trong tài khoản của bạn); có các phiên bản khác (mlocate, slocate) lập chỉ mục tất cả các tệp và có locatechương trình lọc cơ sở dữ liệu để chỉ trả về các tệp bạn có thể thấy.

locate filename

Đôi khi bạn nghĩ rằng một tệp được cung cấp bởi một gói trong bản phân phối của bạn, bạn biết (một phần) tên của tệp nhưng không phải là tên của gói của bạn và bạn muốn cài đặt gói. Nhiều bản phân phối cung cấp một công cụ cho điều đó. Trên Ubuntu, nó apt-file search filename. Đối với các lệnh tương đương trên các hệ thống khác, hãy kiểm tra Pacman Rosetta .


Ước gì tôi có thể bỏ phiếu này một lần nữa. Chỉ cần tìm kiếm điều này cho một dự án khác tối nay. Cảm ơn một lần nữa, @Gilles!
Iszi

6

tương đương với ví dụ DOS của bạn sẽ là:

cd /
find . -name \*filename\* -print

-printMặc dù vậy, trên Linux, bạn không cần phải tranh luận nữa. Nếu bạn thấy mình làm việc trên các hệ điều hành khác, có thể thuận tiện để biết về nó.


5

Nếu bạn muốn một cái gì đó "nhanh" , nhưng không phải trong một tình huống quan trọng và bạn chỉ muốn biết nếu nó tồn tại và nó ở đâu, bạn có thể sử dụng locate. Nó giữ một cơ sở dữ liệu của tất cả các tệp trong các thư mục mà bạn đã nói với nó để thu thập thông tin trên.

Trong cài đặt mặc định (trên Ubuntu), locatethiết lập croncông việc hàng ngày để quét hệ thống tệp và cập nhật cơ sở dữ liệu ...

Nếu bạn cảm thấy cần phải cập nhật cơ sở dữ liệu trước khi cập nhật cron tiếp theo, nó thường nhanh hơn findhoặc lschỉ chạy sudo updatedbvà sau đó locate. Nó chắc chắn sẽ nhanh hơn nếu bạn cần thực hiện nhiều tìm kiếm hơn ... như tên gọi của nó, updatedbcập nhật cơ sở dữ liệu locatesử dụng ...

locatecó regex tích hợp, điều này làm cho nó rất tiện dụng ... Tôi sẽ sử dụng findtrong một tập lệnh, nhưng tôi hiếm khi sử dụng findở dòng lệnh. Tôi thậm chí sử dụng locatetrong các kịch bản (cá nhân) ... ví dụ.locate -bir "oo.*datt.*mp4$"

locate trả về các đường dẫn đủ điều kiện của các tập tin phù hợp.


2
find [path] -name [filename]

Ví dụ: nếu tôi muốn tìm kiếm thư mục / home cho tên tệp chứa foo, tôi sẽ sử dụng lệnh:

find /home -name *foo*

sử dụng lệnh man findđể biết thêm thông tin về lệnh find và đối số,


3
Bạn cần trích dẫn hoặc thoát khỏi *s để ngăn shell giải thích chúng.
Shawn J. Goff

Là distro / shell cụ thể? Tôi đã chạy nó trong Fedora 16 mà không thoát được và nó hoạt động tốt.
josh-cain

1
Có một số tùy chọn trong một số vỏ vượt qua các ngôi sao trong chương trình nếu chúng không xảy ra để khớp với bất cứ thứ gì. Hãy thử tạo một tệp trong thư mục hiện tại của bạn phù hợp với mẫu đó và thử lại lệnh.
Shawn J. Goff
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.