2012-11-22 27 views
8

tôi muốn biết sự khác biệt giữa 2 lệnh dưới đây, tôi hiểu rằng 2) nên sử dụng nhưng tôi muốn biết chuỗi chính xác xảy ra trong 1) và 2) giả sử tên tệp có 200 ký tự trong đókhác biệt giữa grep Vs cat và grep

1) tên tệp cat | grep regex

2) grep regex filename

Trả lời

0

Về mặt chức năng họ là tương đương, tuy nhiên, lớp vỏ sẽ ngã ba hai quá trình cho cat filename | grep regex và kết nối chúng với một ống.

4

Đầu tiên một:

cat filename | grep regex 

Thông thường mèo mở tập tin và in dòng nội dung của nó bởi dòng để stdout. Nhưng ở đây nó xuất ra nội dung của nó thành đường ống '|'. Sau đó grep đọc từ đường ống (nó có đường ống như stdin) sau đó nếu phù hợp với regex in dòng để stdout. Nhưng ở đây có một grep chi tiết được mở trong quá trình shell mới, do đó pipe chuyển tiếp đầu vào của nó như đầu ra cho quá trình shell mới.

Second một:

grep regex filename 

Đây grep trực tiếp đọc từ tập tin (trên nó đã được đọc từ ống) và phù hợp với regex nếu bản in xuất hiện dòng stdout.

+0

+1: pedant (ví dụ như tôi) có thể tranh luận rằng 'cat' luôn ghi vào đầu ra tiêu chuẩn của nó, nhưng trong ngữ cảnh của đường ống, đầu ra tiêu chuẩn của nó là đầu viết của một đường ống. Tương tự, khi 'grep' được gọi không có đối số tên tệp hoặc khi nó xử lý đối số tên tệp của' -', nó sẽ đọc đầu vào tiêu chuẩn của nó, trong trường hợp này, là đầu đọc của đường ống. Lưu ý rằng 'pipe' hoặc' | 'không phải là một lệnh; nó không phải là khá rõ ràng cho dù bạn nhận ra rằng với 'để ống chuyển tiếp đầu vào của nó như là đầu ra cho quá trình shell mới'. –

14

Chức năng (về mặt đầu ra), hai giá trị này giống nhau. Việc đầu tiên thực sự tạo ra một quá trình riêng biệt cat mà chỉ đơn giản là gửi nội dung của tập tin đầu ra tiêu chuẩn, trong đó cho thấy trên đầu vào tiêu chuẩn của grep, bởi vì vỏ đã kết nối hai với một đường ống.

Trong ý nghĩa đó, grep regex <filename cũng tương đương nhưng với một quy trình ít hơn.

Tại nơi bạn sẽ bắt đầu thấy sự khác biệt là trong các biến thể khi thông tin thêm (tên tập tin) là sử dụng bởi grep, chẳng hạn như với:

grep -n regex filename1 filename2 

Sự khác biệt giữa đó và:

cat filename1 filename2 | grep -n regex 

là cựu biết về các tập tin cá nhân trong khi sau này thấy nó như là một tập tin (không có tên).

Trong khi trước đây có thể cung cấp cho bạn:

filename1:7:line with regex in 10-line file 
filename2:2:another regex line 

sau này sẽ được nhiều hơn như:

7:line with regex in 10-line file 
12:another regex line 

Một thực thi hoạt động khác nếu nó biết tên tập tin là wc, các các chương trình truy cập từ:

$ cat qq.in 
1 
2 
3 

$ wc -l qq.in   # knows file so prints it 
3 qq.in 

$ cat qq.in | wc -l  # does not know file 
3 

$ wc -l <qq.in   # also does not know file 
3 
1

Nếu bạn muốn kiểm tra diffrence thời gian thực hiện thực tế, lần đầu tiên tạo ra một tập tin với 100000 dòng:

[email protected] ~ $ for i in $(seq 1 100000); do echo line${1} >> test_f; done 
[email protected] ~ $ wc -l test_f 
100000 test_f 

Bây giờ đo:

[email protected] ~ $ time grep line test_f 
#... 
real 0m1.320s 
user 0m0.101s 
sys  0m0.122s 

[email protected] ~ $ time cat test_f | grep line 
#... 
real 0m1.288s 
user 0m0.132s 
sys  0m0.108s 

Như chúng ta có thể thấy, diffrence không phải là quá lớn. ..

+0

Lệnh 'time' thứ hai có thời gian là' cat' hoặc toàn bộ đường dẫn không? –

+3

Bao nhiêu thời gian bạn quan sát được là do đầu ra bị bỏ qua được ghi vào màn hình? Tôi đã cố gắng với đầu ra của 'grep' chuyển hướng đến'/dev/null' và có thời gian trong khoảng 10-50 ms, không phải là 1 giây. Bây giờ, máy của tôi không bị chậm chạp, nhưng nhanh hơn 20 lần so với máy của bạn có vẻ khó xảy ra (thậm chí cho phép tập tin đó hầu như nằm trong bộ nhớ, không phải trên đĩa). Rất khó để làm điểm chuẩn tốt. Những gì tôi sợ bạn đang đo là thời gian để viết 100.000 dòng cho thiết bị đầu cuối của bạn, chứ không phải là hiệu suất thô của 'grep' so với' cat | grep'. –

+0

Bạn có thể đúng, tôi chưa tính đến điều đó. – dstronczak

0

Thực ra, mặc dù kết quả đầu ra giống nhau;

-$cat filename | grep regex 

Lệnh này tìm nội dung của tệp "tên tệp", sau đó tìm nạp regex trong đó; trong khi

-$grep regex filename 

Lệnh này trực tiếp tìm kiếm các nội dung tên regex trong file "filename"