मैं grep मिलान के बाद किसी फ़ाइल में लाइनों की संख्या कैसे गिन सकता हूं?


14

मैं एक सीएसवी फ़ाइल में एक समस्याग्रस्त पंक्ति के बाद लाइनों की संख्या को गिनने की कोशिश कर रहा हूं। मुझे पता है कि मैं grep -a #एक मिलान के बाद लाइनों के # संख्या को आउटपुट करने के लिए वाक्यविन्यास का उपयोग कर सकता हूं । मुझे केवल वास्तविक संख्या लाइनों में रुचि है। मुझे लगता है कि मैं अधिकतम संख्या को MAX_INT पर सेट कर सकता हूं, इसे एक फ़ाइल में पाइप कर सकता हूं और कुछ और प्रसंस्करण कर सकता हूं।

मैं एक रसीला वन-लाइनर की तलाश में हूं, बस मुझे गिनती बताएं।

कोई सुझाव?

जवाबों:


15
{ grep -m1 match; grep -c ''; } <file

यह w / GNU grepऔर एक lseek()सक्षम शिशु का काम करेगा । पहला grep1 -match पर रुकेगा , और दूसरा -cइनपुट में बची हुई हर लाइन को पूरा करेगा ।

GNU के बिना grep:

{ sed '/match/q'; grep -c ''; } <file

बेशक, डब्ल्यू / grepआप इसके अलावा किसी भी / सभी अन्य विकल्पों का उपयोग कर सकते हैं, और एक मैच में रोकना बिल्कुल भी आवश्यक नहीं है।


ये दोनों भी लाइन प्रिंट करते हैं, और दूसरा पहले मैच तक प्रिंट करता है और फिर मेरे लिए 0?
123

@ User112638726 - आप निश्चित रूप से पहले मैच का प्रिंटआउट छोड़ सकते हैं grep -m1 match >/dev/null। और आपकी दूसरी समस्या एक GNU है sed- यह अपने इनपुट ऑफसेट प्रति युक्ति को रीसेट नहीं करता है। आपको -uw / GNU का उपयोग करना होगा - जो हमेशा वांछनीय नहीं होता है। मैं स्पष्ट हो सकता था, लेकिन मेरी धारणा यह थी कि एक GNU grepऔर GNU sedजोड़े में आएंगे। मुझे लगता है, यह भी, पुनर्निर्देशन grep -qm1को शार्टकट करने के लिए काम कर सकता है /dev/null- लेकिन GNU grepअजीब चीजें करता है w / -qऔर मुझे याद नहीं है कि वे दोनों एक साथ कैसे काम करते हैं।
15 अक्टूबर को सुबह

1
अच्छा जवाब - वास्तव में कमांड ग्रुपिंग की शक्ति को प्रदर्शित करता है। मुझे यकीन नहीं है, लेकिन मुझे लगता wc -lहै कि थोड़ा सस्ता है grep -c ''
डिजिटल ट्रॉमा

1
@DigitalTrauma - हाँ, मैंने इसे (पूर्वव्यापी में) माना था , लेकिन मैं पहले ही इसे लिख चुका था, और यह लगभग तुकबंद है, इसलिए मुझे लगा कि मैं अकेले बहुत अच्छा करूँगा। और वैसे भी, आपने यह भी कहा था, इसलिए मैं अब आसानी से सो जाऊंगा।
दिसंबर को रात

9

यहाँ एक तरीका है।

$ cat foo
aaa
bbb
ccc
ddd
eee
fff
$ awk '/^ddd/{a=FNR}END{print FNR-a}' foo
2
$

4
यह कोडगुल्फ़ नहीं है, क्या आप विवरण दे सकते हैं (FNR, END और इसी तरह)?
आर्केमॉन

3
ज़रूर। awk इनपुट रिकॉर्ड संख्या की पहचान करने के लिए FNR का उपयोग करता है। END फ़ाइल के अंत तक पहुंचने पर निष्पादित कोड है। इसलिए जब एक मैच पाया जाता है, तो वर्तमान रिकॉर्ड संख्या दर्ज की जाती है। फ़ाइल के अंत तक पहुँचने पर, वह संख्या फ़ाइल में कुल पंक्तियों की संख्या से घटा दी जाती है।
स्टीव

1
हो सकता है कि बस एनआर का उपयोग करें क्योंकि यह एक फाइल है।
123

6

एक और तरीका - का उपयोग dcथोड़ा गूढ़ है, लेकिन यहाँ अच्छी तरह से काम करने लगता है:

sed -n '/problem/=;$=' prob.txt | dc -e '??r-p'

sedखोजें prob.txt"समस्या" और अंतिम पंक्ति है, और उपयोग के लिए =उत्पादन के लिए आदेश दोनों की लाइन नंबर।

dc स्टैक पर इन दो मूल्यों को पढ़ता है, उन्हें उलट देता है, अंतर को हटाता है और प्रिंट करता है।


5

पूरी तरह से सेड (यद्यपि एक पाइप के साथ दो कमांड)

sed '/ddd/,$!d' file | sed -n '$='

पंक्ति से पहले सभी रेखाओं को हटाता है और फिर अगली कमांड नई फ़ाइल में रेखाओं को गिनता है।


3

इससे समस्याग्रस्त एक (और सहित) तक की सभी पंक्तियों को हटा देना चाहिए और फिर शेष पंक्तियों को गिनना चाहिए:

sed '1,/problem/d' data.txt | wc -l

1
(यह मानते हुए कि "समस्या" पहली पंक्ति में नहीं है)
स्टीफन चेज़ेलस
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.