Làm thế nào để có được dòng dài nhất từ ​​một tập tin?


10

Tôi muốn tìm ra số dòng của dòng dài nhất từ ​​một tệp.

Ví dụ: nếu tôi có một tệp có nội dung sau:

lalala
tatatata
abracadabra
mu mu mu

Làm thế nào tôi có thể viết một tập lệnh bash sẽ cho tôi một kết quả như thế này : 3 -> abracadabra?

Câu trả lời:


9

Bạn không cần một kịch bản để làm điều này. Một lệnh đơn giản là đủ:

egrep -n "^.{$(wc -L < filename)}$" filename

Điều này sẽ hoạt động ngay cả khi bạn có hai hoặc nhiều dòng có cùng độ dài tối đa.

Nếu bạn muốn đầu ra chính xác ở dạng này : 3 -> abracadabra, thì sử dụng:

egrep -n "^.{$(wc -L < filename)}$" filename | sed 's/:/ -> /'

Người giới thiệu:


3
@ don.joey: đó là sức mạnh của unix. Các lệnh đơn giản, có thể làm việc cùng nhau. Ở đây, anh ta tìm "^. {n} $", tức là bất kỳ dòng nào, giữa đầu dòng ( ^) và cuối của nó ( $) có chính xác n ký tự ( .{n}). Sau đó, anh ta chỉ cần tìm n: vì điều này anh ta sử dụng một GNU-ism, "tên tệp wc -L" (lưu ý rằng đây không phải là posix) trả về độ dài của dòng tên dài nhất. Vì vậy, anh ấy chào bất kỳ dòng nào có chiều dài dài nhất. $(cmd)được thay thế bởi đầu ra của cmd.
Olivier Dulac

1
@OlivierDulac Nhận xét tuyệt vời.
Radu Rădeanu

Thậm chí tốt hơn, bạn cũng có thể thêm (ví dụ) -C 3vào các tùy chọn grep để nhận một vài dòng trước và sau cho bối cảnh
ShadSterling

8

Bạn có thể sử dụng awkđể in độ dài của mỗi dòng ( length()) và số dòng ( NR), sau đó đảo ngược ( -r) sortkết quả theo số ( -n):

$ awk '{ print length(), NR, $0 | "sort -rn" }' tmp.txt
10 3 abracadabr
8 4 mu mu mu
7 2 tatatat
6 1 lalala

Để chỉ hiển thị dòng đầu tiên:

$ awk '{ print length(), NR, $0 | "sort -rn" }' tmp.txt | head -n 1
10 3 abracadabr

@ user214965 vui lòng xem cập nhật của tôi, số dòng được hiển thị là số thứ hai trong kết quả.
Attila O.

Nếu có 2 dòng có cùng độ dài tối đa thì sao?
Radu Rădeanu

@ RaduRădeanu điểm tốt. +1 cho wc -L, tôi không biết về lập luận đó. Nó thực sự rất hữu ích.
Attila O.

4

AO (N) có thể đạt được với một lớp lót perl:

perl -e 'while (<>) { if (length > length $max) { $max=$_}}; print $max'

tập quán (trong đó machin là tên tập tin)

cat machin | perl -e 'while (<>) { if (length > length $max) { $max=$_}}; print $max'

hoặc là

perl -e 'while (<>) { if (length > length $max) { $max=$_}}; print $max' machin

hoặc (ít rõ ràng hơn nhưng ngắn hơn)

perl -ne 'if(length>length$m){$m=$_};END{print$m}' machin

Nhiều, hiệu quả hơn nhiều. Cảm ơn! Đã tìm kiếm nó.
kiểm tra

1
Hoạt động với các tệp khổng lồ +1
h3xStream

0

O (n) Đối với máy móc, ví dụ OpenWRT, nơi không có sẵn perl, phiên bản @ awk @ có thể hữu ích.

awk 'length > l {l=length;line=$0} END {print line}' FILE

hoặc trăn:

python -c "print max(open('$file', 'r'), key=len)"

0

Câu trả lời của Radu là hoàn toàn đủ và được ưa thích, mặc dù nếu bạn muốn giải pháp rõ ràng hơn và dựa trên vỏ, thì bạn có thể sử dụng tập lệnh sau:

#!/bin/bash
longest_length=0
longest_string=0
while IFS= read -r line || [ -n "${line}"]
do
    if [ "${#line}" -gt "${longest_length}" ]
    then
        longest_length="${#line}"
        longest_string="$line"
    fi
done < "$1"

echo "${longest_string}"

Sử dụng: ./find_longest.sh input.txt

Thí dụ:

$ cat input.txt                                                          
1 2 
2 3 a a a a
4 5 6 
1 1 1 5

$ ./find_longest.sh input.txt                                            
2 3 a a a a
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.