Câu hỏi của bạn liên quan chặt chẽ đến cách trình bao bạn đang sử dụng phân tích cú pháp đầu vào của người dùng trên dòng lệnh.
Nếu từ đầu tiên trên dòng lệnh là một chương trình, nằm trong một thư mục đặc biệt (chủ yếu được xác định bởi PATH
) và không có ký tự đặc biệt nào được đưa ra (tùy thuộc vào trình bao bạn đang sử dụng), tất cả các từ tiếp theo được phân tách bằng dấu cách hoặc tab được chuyển đến chương trình ở dạng đặc biệt tức là một mảng. Với mỗi từ là một yếu tố trong mảng.
Làm thế nào chương trình, bạn sẽ gọi phiên dịch các đối số (nằm trong mảng) phụ thuộc vào cách nó được lập trình. Có một số tiêu chuẩn gần đúng về cách cú pháp của các đối số sẽ trông như thế nào nhưng nói chung, lập trình viên hoàn toàn miễn phí. Vì vậy, đối số đầu tiên có thể được hiểu là tên của một tệp hoặc bất cứ điều gì lập trình viên nghĩ đến tại thời điểm ông viết chương trình.
Trong trường hợp bạn thêm ký tự đặc biệt <
hoặc >
vào dòng lệnh của mình, shell sẽ không nối <
và >
các từ tiếp theo vào mảng sẽ được chuyển đến chương trình. Với <
hoặc >
được cung cấp, shell bắt đầu tạo ra những thứ ưa thích, được hỗ trợ bởi kernel bên dưới ( đường ống từ khóa ). Để nắm bắt những gì đang diễn ra, bạn phải hiểu những gì STDIN
và STDOUT
(vì nó không liên quan ngay lập tức tôi bỏ qua STDERR
).
Mọi thứ bạn có thể nhìn thấy trên thiết bị đầu cuối của bạn (trong hầu hết các trường hợp, một phần của màn hình của bạn) được ghi bởi trình bao hoặc bất kỳ chương trình nào khác mà bạn đã gọi trước đó vào một tệp đặc biệt (trong unix mọi thứ đều là một tệp ). Tập tin này có một id đặc biệt và được gọi STDOUT
. Nếu một chương trình muốn đọc dữ liệu từ bàn phím, nó sẽ không thăm dò trực tiếp bàn phím (ít nhất là trong hầu hết các trường hợp) nhưng đọc từ một tệp đặc biệt được gọi STDIN
. Trong nội bộ tập tin này được kết nối với thiết bị đầu vào tiêu chuẩn của bạn, bàn phím của bạn trong hầu hết các trường hợp.
Nếu shell đọc <
hoặc >
trong một dòng lệnh được phân tích cú pháp, nó sẽ thao tác STDIN
hoặc STDOUT
trong một loại cụ thể trong thời gian chương trình tương ứng đang chạy. STDIN
và không STDOUT
chỉ đến thiết bị đầu cuối hoặc thiết bị đầu vào tiêu chuẩn nữa mà thay vào đó là tên tệp tiếp theo trên dòng lệnh.
Trong trường hợp của hai dòng
cat file_name
cat < file_name
hành vi được quan sát là giống hệt nhau vì nhà phát triển tương ứng thực hiện cat
để đọc dữ liệu từSTDIN
hoặc đọc dữ liệu từ tệp, tên được đặt làm đối số dòng lệnh đầu tiên (là thành phần đầu tiên trong mảng mà shell truyền đến cat
). Sau đó, cat
viết toàn bộ nội dung của file_name
hoặc STDIN
cho thiết bị đầu cuối vì chúng tôi không hướng dẫn trình vỏ thao tác STDOUT
. Hãy nhớ rằng trong dòng thứ hai, shell của bạn thao tác STDIN
theo cách này, nó không trỏ đến thiết bị đầu vào tiêu chuẩn của bạn nữa mà chỉ vào một tệp được gọi file_name
trong thư mục làm việc hiện tại của bạn.
Trong trường hợp khác của dòng
man < file_name
man
không có nghĩa là đọc bất cứ thứ gì STDIN
nếu nó được gọi mà không có đối số tức là một mảng trống. Vì vậy, dòng
man < file_name
bằng
man
Ví dụ man
sẽ đọc một cái gì đó từ STDIN
, quá nếu bạn vượt qua -l -
để man
. Với tùy chọn này được cung cấp trên dòng lệnh, bạn có thể hiển thị nội dung của mọi thứman
đọc từ STDIN
trên thiết bị đầu cuối của bạn. Vì thế
man -l - < file_name
cũng sẽ hoạt động (nhưng hãy cẩn thận man
không chỉ là máy nhắn tin mà còn phân tích cú pháp đầu vào của tệp và do đó nội dung tệp và nội dung được hiển thị có thể khác nhau).
Vậy làm thế nào STDIN
, STDOUT
và các đối số dòng lệnh được hiểu là tất cả các thiết lập của nhà phát triển tương ứng.
Tôi hy vọng câu trả lời của tôi có thể làm sáng tỏ mọi thứ.
man -l - < file_name
đểman
diễn giảiSTDIN
thành đối số, nhưng nó thất bại trong hệ thống của tôi vớiSTDERR
:man -l - < tee man: invalid option -- l man, version 1.6c