Grep เริ่มต้นจากข้อความคงที่จนกระทั่งบรรทัดว่างแรก


9

ฉันมีไฟล์prova.txtเช่นนี้:

Start to grab from here: 1
fix1
fix2
fix3
fix4
random1
random2
random3
random4

extra1
extra2
bla

Start to grab from here: 2
fix1
fix2
fix3
fix4
random1546
random2561

extra2
bla
bla

Start to grab from here: 1
fix1
fix2
fix3
fix4
random1
random22131

และฉันต้อง grep out จาก "Start to grab here" ถึงบรรทัดว่างบรรทัดแรก ผลลัพธ์ควรเป็นดังนี้:

Start to grab from here: 1
fix1
fix2
fix3
fix4
random1
random2
random3
random4

Start to grab from here: 2
fix1
fix2
fix3
fix4
random1546
random2561

Start to grab from here: 1
fix1
fix2
fix3
fix4
random1
random22131

ในขณะที่คุณสามารถดูบรรทัดหลังจาก "เริ่มที่จะคว้าที่นี่" เป็นแบบสุ่มดังนั้น -A -B grep flag ไม่ทำงาน:

cat prova.txt | grep "Start to grab from here" -A 15 | grep -B 15 "^$" > output.txt

คุณช่วยฉันค้นหาวิธีที่จะจับบรรทัดแรกที่จะถูกจับ (เช่น "เริ่มที่จะคว้าจากที่นี่") จนกระทั่งบรรทัดว่าง ฉันไม่สามารถคาดเดาได้ว่าฉันจะมีจำนวนบรรทัดสุ่มหลังจาก "เริ่มที่จะคว้าจากที่นี่"

โซลูชันที่เข้ากันได้กับยูนิกซ์คือคำขอบคุณ (grep, sed, awk ดีกว่า perl หรือคล้ายกัน)

แก้ไข: หลังจากการตอบสนองที่ยอดเยี่ยมโดย @ john1024 ฉันต้องการทราบว่าเป็นไปได้หรือไม่:

1 °เรียงบล็อก (ตามที่จะเริ่มจากที่นี่: 1 แล้ว 1 และ 2)

2 °ลบ 4 (ตัวอักษรสุ่ม) บรรทัด fix1, fix2, fix3, fix4 แต่มักจะ 4

3 °ในที่สุดก็เอาการสุ่มแบบคู่เช่นคำสั่ง sort -u

ผลลัพธ์สุดท้าย shoul เป็นเช่นนี้:

# fix lines removed - match 1 first time
Start to grab from here: 1
random1
random2
random3
random4

#fix lines removed - match 1 second time
Start to grab from here: 1
#random1 removed cause is a dupe
random22131

#fix lines removed - match 2 that comes after 1
Start to grab from here: 2
random1546
random2561

หรือ

# fix lines removed - match 1 first time and the second too
Start to grab from here: 1
random1
random2
random3
random4
#random1 removed cause is a dupe
random22131

#fix lines removed - match 2 that comes after 1
Start to grab from here: 2
random1546
random2561

เอาต์พุตที่สองนั้นดีกว่าอันแรก จำเป็นต้องใช้เวทมนตร์คำสั่ง unix อื่น ๆ


1
สิ่งนี้มีประโยชน์มากสำหรับการจับการติดตามสแต็กสำหรับเธรดเฉพาะจากเอาต์พุต jstack ของ Java ดีใจที่พบคำถาม & คำตอบนี้!
BenjaminBallard

คำตอบ:


13

ใช้ awk

ลอง:

$ awk '/Start to grab/,/^$/' prova.txt
Start to grab from here: 1
random1
random2
random3
random4

Start to grab from here: 2
random1546
random2561

Start to grab from here: 3
random45
random22131

/Start to grab/,/^$/กำหนดช่วง มันเริ่มต้นด้วยบรรทัดใด ๆ ที่จับคู่Start to grabและลงท้ายด้วยบรรทัดว่างบรรทัดแรก^$ที่ตามมา

การใช้ sed

ด้วยตรรกะที่คล้ายกันมาก:

$ sed -n '/Start to grab/,/^$/p' prova.txt
Start to grab from here: 1
random1
random2
random3
random4

Start to grab from here: 2
random1546
random2561

Start to grab from here: 3
random45
random22131

-nบอกไม่ให้พิมพ์สิ่งใดนอกจากเราจะขอให้ชัดเจน /Start to grab/,/^$/pบอกว่ามันพิมพ์บรรทัดใด ๆ /Start to grab/,/^$/ในช่วงที่กำหนดโดย


โซลูชันของคุณสมบูรณ์แบบฉันได้แก้ไขการขอเพิ่มบางอย่าง ขอขอบคุณสำหรับความช่วยเหลือของคุณ ขอบคุณ
heisen

1

ฉันกำลังโพสต์โซลูชันทางเลือกเนื่องจากอาจเป็นประโยชน์กับบางคนใช้เคส วิธีการแก้ปัญหานี้ไม่เป็นไปตามข้อกำหนดที่ระบุไว้อย่างชัดเจนเพื่อดูคำตอบที่ดีที่สุดจาก @ John1024

คุณสามารถใช้ awk โดยตั้งค่าตัวคั่นเร็กคอร์ดเป็นสตริงว่าง awk จะตีความสิ่งเหล่านี้เป็นบรรทัดว่างเปล่า:

$ awk '/Start/' RS= prova.txt 
Start to grab from here: 1
fix1
fix2
fix3
fix4
random1
random2
random3
random4
Start to grab from here: 2
fix1
fix2
fix3
fix4
random1546
random2561
Start to grab from here: 1
fix1
fix2
fix3
fix4
random1
random22131

รุ่นนี้ไม่ได้ขึ้นบรรทัดใหม่ว่างเปล่าในการส่งออก นอกจากนี้ยังจะแสดงบริบทก่อนการแข่งขันหากมี พฤติกรรมนี้มีประโยชน์มากเมื่อ grepping สำหรับบางสิ่งบางอย่างในไฟล์และคุณต้องการดูบล็อกตัวคั่นที่ขึ้นบรรทัดใหม่ซึ่งเป็นส่วนหนึ่งของ:

$ awk '/random1546/' RS= prova.txt 
Start to grab from here: 2
fix1
fix2
fix3
fix4
random1546
random2561

เช่นฉันพบว่ามีประโยชน์เมื่อ grepping สำหรับสิ่งต่าง ๆ ในiniไฟล์

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.