Lệnh này hợp pháp như thế nào? Mùi> file1 <file2 cat


61

Giả sử file2đã tồn tại, lệnh

> file1 < file2 cat

dường như được sao chép nội dung của file2để file1.

Nhưng tôi không thể hiểu cấu trúc này.

Tôi hiểu rằng "Không có gì" đang được hướng đến file1, (tạo hoặc xóa nội dung của nó). Sau đó, nội dung của file2đang được hướng đến file1.

Tại sao là catsau file2? Làm thế nào để biết cat file2nếu các toán hạng không theo đúng thứ tự?


11
"Trật tự đúng" là gì? Bạn có thể cung cấp một liên kết đến một số tài liệu / tài liệu học tập trong đó một "thứ tự đúng" được mô tả không?
Cuộc đua nhẹ nhàng với Monica

7
Khi đặt câu hỏi như thế này, bạn nên chỉ định shell; những cái khác nhau có trường hợp cạnh khác nhau, đặc biệt là xung quanh chuyển hướng.
chrylis -on đình công-

Câu trả lời:


117

Trước khi shell thực thi catlệnh trên dòng lệnh, nó sẽ tìm chuyển hướng.

Có hai chuyển hướng:

  1. >file1 Điều này sẽ làm cho đầu ra tiêu chuẩn của lệnh đi đến file1.
  2. <file2 Điều này sẽ làm cho đầu vào tiêu chuẩn của lệnh đến từ file2.

Việc các chuyển hướng này được đặt ở một vị trí thuận lợi trên dòng lệnh không thành vấn đề.

$ cat <file2 >file1

giống như

$ <file2 cat >file1

giống như

$ <file2 >file1 cat

v.v ...

Lưu ý rằng cattiện ích trong tất cả các trường hợp này được thực thi mà không có bất kỳ đối số dòng lệnh nào . Các chuyển hướng không phải là toán hạng cho catlệnh, chúng là các lệnh cho shell để thiết lập các chuyển hướng vào và ra lệnh (kết nối đầu vào và đầu ra tiêu chuẩn của nó với các tệp). Shell thiết lập các chuyển hướng trước khi gọi lệnh.

Sự khác biệt giữa cat filecat <file(hoặc, nếu bạn sẽ, <file cat) là trong trường hợp đầu tiên, catchính tiện ích đang mở tệp, được đưa ra dưới dạng toán hạng trên dòng lệnh, để đọc, trong trường hợp thứ hai, trình bao sẽ mở tệp và kết nối catluồng đầu vào của nó với it². Trong trường hợp thứ hai, catsẽ nhận thấy rằng nó không được cung cấp một toán hạng tệp và sẽ tự động chuyển sang đọc từ đầu vào tiêu chuẩn của nó. Đây là một tính năng của catvà một số tiện ích khác, không phải là thứ mà tất cả các tiện ích đều làm được.

catcũng sẽ đọc từ đầu vào tiêu chuẩn của nó nếu nó được đưa ra toán hạng -. Một lần nữa, điều này chỉ đặc biệt đối với catvà đối với một số tiện ích khác (tức là không có gì mà shell làm được). Để sử dụng cattrên một tập tin trong thư mục hiện có tên - , thêm một đường dẫn đến tên tập tin, chẳng hạn như ./-.

¹ Thứ tự của các chuyển hướng là vẫn quan trọng trong một số hoàn cảnh; Với cat <file2 >file1, ví dụ, file1sẽ không được rút ngắn nếu file2là không thể tiếp cận (các chuyển hướng được phân tích cú pháp từ trái sang phải). catTuy nhiên, vị trí tương đối của từ này vẫn tùy ý và sẽ không ảnh hưởng đến điều này.

² Xem thêm câu hỏi " con mèo đưa ra lỗi khác nhau khi mở tệp không tồn tại ".


Việc shell thiết lập các chuyển hướng trước khi thực hiện lệnh trên dòng lệnh là lý do tại sao những thứ như thế này thất bại và bạn kết thúc với một tệp đầu ra trống:

$ sort file >file

Ở đây, shell sẽ cắt bớt (trống) tệp filetrước khi thực hiện sort filevà kết nối sortđầu ra tiêu chuẩn của tệp với tệp. Các sorttiện ích sau đó sẽ mở ra filevà sắp xếp nội dung của nó (đó là gì). Kết quả (không có gì) được truyền qua luồng đầu ra tiêu chuẩn đến file.

Biện pháp khắc phục trong trường hợp cụ thể này (để sắp xếp một tệp "tại chỗ") là

$ sort -o file file

hoặc là

$ sort file >file.sorted && mv file.sorted file

đó là nhiều hay ít những gì sortlàm khi sử dụng -otệp để chỉ định tên tệp đầu ra.


Chỉ cần sao lưu tuyên bố rằng các chuyển hướng có thể đặt trước tên thực của tiện ích trên dòng lệnh:

"Lệnh đơn giản" là một chuỗi các phép gán và chuyển hướng tùy chọn, trong bất kỳ chuỗi nào, tùy ý theo sau là các từ và chuyển hướng, được chấm dứt bởi một toán tử điều khiển. [ref: POSIX Shell Ngôn ngữ lệnh 2.9.1 Các lệnh đơn giản]

Và cũng về việc chuyển hướng không phải là một phần của toán hạng của tiện ích:

Số tùy chọn, toán tử chuyển hướng và từ sẽ không xuất hiện trong các đối số được cung cấp cho lệnh sẽ được thực thi (nếu có). [ref: POSIX Shell Ngôn ngữ lệnh 2.7 Chuyển hướng]


14
@Steve Tự do di chuyển các chuyển hướng xung quanh có thể được sử dụng để làm cho một số lệnh rõ ràng hơn, giống như một đường ống với chuyển hướng đầu vào lúc đầu <in foo | bar >outđặt mọi thứ theo thứ tự hợp lý. Tôi cũng thích nếu echo >&2 Something bad happenedđầu ra lỗi từ shell script. Nhưng >out <in catchỉ là obfuscation

2
Làm thế nào có thể sort file >fileđược thực hiện chính xác?
seth10

11
@setht Với sort -o file file.
Kusalananda

6
Câu trả lời chính xác. Lưu ý rằng vấn đề đặt hàng. < file1 > file2 catsẽ tốt hơn > file2 < file1 catvì điều đó sẽ tránh file2bị cắt cụt nếu file1không thể mở được.
Stéphane Chazelas

3
Một điều cần chú ý: khi liên kết với POSIX với các đoạn HTML, tốt hơn là chỉ định phiên bản chính xác (như pubs.opengroup.org/onlinepub/9699919799.2016edition ) vì các đoạn đã được biết là thay đổi giữa các phiên bản của cùng một phiên bản (rất nhiều liên kết trong câu trả lời trên trang web này, bao gồm cả của tôi hiện đang sai vì các đoạn bị sai ở vị trí sau khi phiên bản 2016 đã được phát hành).
Stéphane Chazelas
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.