একটি লাইনে দুটি শব্দ অনুসন্ধান করে গ্রেপ করুন


46

আমি একটি লাইন ফিল্টার করার জন্য একটি উপায় খুঁজতে চেষ্টা করেছি যেখানে এতে "লেবু" এবং "চাল" শব্দ রয়েছে। আমি জানি "কীভাবে" লেবু "বা" চাল "পাওয়া যায় তবে সেগুলির দুটি নয়। তাদের অন্যের পাশে থাকা দরকার নেই, কেবল পাঠ্যের একই লাইনের।


1
কোনও ফাইলের অভ্যন্তরে থাকা সমস্ত স্ট্রিং সন্ধান করতে আপনি ফর লুপে গ্রেপ
নোয়াম মানস

উত্তর:


62

"একই লাইনে উভয়ই" এর অর্থ "ভাত 'এর পরে এলোমেলো অক্ষর এবং তারপরে' লেবু 'বা অন্য পথে"।

রেজেক্সে যা হয় rice.*lemonবা lemon.*rice। আপনি এটি ব্যবহার করে একত্রিত করতে পারেন |:

grep -E 'rice.*lemon|lemon.*rice' some_file

আপনি যদি বর্ধিতদের ( -E) এর পরিবর্তে সাধারণ রেজেক্স ব্যবহার করতে চান তবে আপনার আগে ব্যাকস্ল্যাশ দরকার |:

grep 'rice.*lemon\|lemon.*rice' some_file

আরও শব্দের জন্য যা দ্রুত কিছুটা দীর্ঘ হয় এবং সাধারণত একাধিক কল ব্যবহার করা সহজ grep, উদাহরণস্বরূপ:

grep rice some_file | grep lemon | grep chicken

আপনার শেষ লাইনটি সংমিশ্রণ নয়, বিযুক্তি নয়? বুদ্ধিমান: grep riceলাইনগুলি সমন্বিত সন্ধান করে rice। এটি খাওয়ানো হয় grep lemonযা কেবলমাত্র লেবুযুক্ত লাইনগুলি খুঁজে পাবে .. এবং আরও অনেক কিছু। যেখানে ওপি - পাশাপাশি আপনার পূর্বের উত্তরগুলি - কোনও [চাল | লেবু | মুরগী]
মঞ্জুর করছে জাভদ্বা

স্ক্রিপ্ট সংস্করণ: Askubuntu.com/a/879253/5696
জেফ

@ ফ্লোরিয়ান ডিয়েচ - মাইন্ড ব্যাখ্যা করছেন কেন |ভিতরে পালানো দরকার grep? ধন্যবাদ!
পলাতক

1
@ পলাতক egrepপ্রসারিত রেজেক্স ব্যবহার করে যেখানে |OR যুক্তি হিসাবে বোঝা যায়। grepবেসিক রেজেক্সের ডিফল্ট, যেখানে \|হয়
সের্গেই কলডিয়াজনি

grepএর ম্যানপেজে যেমন বলা হয়েছে , হ্রাস করা egrepহয় এবং এটি দ্বারা প্রতিস্থাপন করা উচিত grep -E। আমি সেই অনুযায়ী উত্তর সম্পাদনা করার স্বাধীনতা নিয়েছি।
মিষ্টান্ন

26

আপনি প্রথম গ্রেপ কমান্ডের আউটপুটটি অন্য একটি গ্রেপ কমান্ডে পাইপ করতে পারেন এবং এটি উভয় ধরণের সাথে মিলবে। সুতরাং, আপনি যেমন কিছু করতে পারেন:

grep <first_pattern> <file_name> | grep <second_pattern>

বা,

cat <file_name> | grep <first_pattern> | grep <second_pattern>

উদাহরণ:

আসুন আমাদের ফাইলে কিছু সামগ্রী যুক্ত করুন:

$ echo "This line contains lemon." > test_grep.txt
$ echo "This line contains rice." >> test_grep.txt
$ echo "This line contains both lemon and rice." >> test_grep.txt
$ echo "This line doesn't contain any of them." >> test_grep.txt
$ echo "This line also contains both rice and lemon." >> test_grep.txt

ফাইলটিতে কী রয়েছে:

$ cat test_grep.txt 
This line contains lemon.
This line contains rice.
This line contains both lemon and rice.
This line doesn't contain any of them.
This line also contains both rice and lemon.

এখন, আমরা যা চাই গ্রেপ করা যাক:

$ grep rice test_grep.txt | grep lemon
This line contains both lemon and rice.
This line also contains both rice and lemon.

আমরা কেবল সেই লাইনগুলি পাই যেখানে উভয় নিদর্শন মেলে। আপনি এটি প্রসারিত করতে পারেন এবং আরও "ও" ম্যাচের জন্য আউটপুটটিকে অন্য গ্রেপ কমান্ডে পাইপ করতে পারেন।


21

যদিও প্রশ্নটি 'গ্রেপ' এর জন্য জিজ্ঞাসা করেছে, আমি ভেবেছিলাম এটি একটি সহজ 'অ্যাডক' সমাধান পোস্ট করতে সহায়ক হতে পারে:

awk '/lemon/ && /rice/'

এটি 'শ' এর সাথে আরও শব্দের সাথে বা অন্য বুলিয়ান এক্সপ্রেশন সহ সহজেই বাড়ানো যেতে পারে।


11

কোনও ক্রমে ম্যাচগুলি সন্ধান করার জন্য অন্য একটি ধারণা ব্যবহার করছে:

সঙ্গে grep -P (পার্ল-সঙ্গতির) বিকল্প এবং ইতিবাচক lookahead Regex(?=(regex)) :

grep -P '(?=.*?lemon)(?=.*?rice)' infile

অথবা আপনি নীচে ব্যবহার করতে পারেন, পরিবর্তে:

grep -P '(?=.*?rice)(?=.*?lemon)' infile
  • শৈলীর সাথে শূন্য বা তার বেশিবার সংঘটিত হওয়ার .*?সাথে সাথে কোনও প্যাটার্ন ( বা ) অনুসরণ করার পরে এর অর্থ হল । সবকিছু ঐচ্ছিক তোলে আগেই (মানে শূন্য বা সবকিছুর এক সময় মিলেছে ).*ricelemon?.*

(?=pattern): ইতিবাচক লুকোহেড: ইতিবাচক লুয়াহেড কন্সট্রাক্ট হ'ল বন্ধনীগুলির একজোড়া, খোলার প্রথম বন্ধনী এবং তারপরে একটি প্রশ্ন চিহ্ন এবং সমান চিহ্ন by

সুতরাং এটি উভয় lemonএবং riceএলোমেলোভাবে ক্রমযুক্ত সমস্ত লাইন ফিরে আসবে । এছাড়াও এটি |এস এবং দ্বিগুণ grepএস ব্যবহার করা এড়ানো হবে ।


বাহ্যিক লিঙ্কগুলি: উন্নত গ্রেপ টপিকগুলি ইতিবাচক লুকোহেড - ডিজাইনারদের জন্য জিআরপি


5
grep -e foo -e goo

Foo বা goo উভয়ের জন্য ম্যাচ ফিরবে


1

যদি আমরা স্বীকার করি যে grepভিত্তির ভিত্তিতে নয় এমন উত্তর সরবরাহ করা গ্রহণযোগ্য, যেমন উপরের উত্তরের উপর ভিত্তি করে awk, তবে আমি একটি সাধারণ perlলাইন প্রস্তাব করব :

$ perl -ne 'print if /lemon/ and /rice/' my_text_file

সন্ধান কিছু / সমস্ত শব্দের সাথে কেস কে উপেক্ষা করতে পারে /lemon/i and /rice/i। বেশিরভাগ ইউনিক্স / লিনাক্সে মেশিন পার্ল ইনস্টল করার পাশাপাশি যেকোনও উপায়ে ইনস্টল করা থাকে।


প্রত্যাখ্যান !!! ;) কারণ এটি কোনও লাভ নেই .. :)
An0n

0

গ্রেপ পাইপিং সমাধানটি স্বয়ংক্রিয় করার জন্য এখানে একটি স্ক্রিপ্ট রয়েছে:

#!/bin/bash

# Use filename if provided as environment variable, or "foo" as default
filename=${filename-foo}

grepand () {
# disable word splitting and globbing
IFS=
set -f
if [[ -n $1 ]]
then
grep -i "$1" ${filename} | filename="" grepand "${@:2}"
else
# If there are no arguments, assume last command in pipe and print everything
cat
fi
}

grepand "$@"

1
এটি সম্ভবত কমান্ড স্ট্রিং তৈরি এবং evalএটির পরিবর্তে পুনরাবৃত্ত ফাংশন ব্যবহার করে প্রয়োগ করা উচিত , যা সহজেই ভেঙে যায়
মুর্গু

@ মুরু একটি নির্দ্বিধায় বিনামূল্যে পরামর্শ দিন। আমি মন্তব্য প্রশংসা করি।
জেফ

1
এটি সম্পাদনা করা পুনর্লিখনের অনেক বেশি হবে, তাই আমি এটি করব না। : আপনি এটি যোগ করতে চান তাহলে, এখানে আমি যা কল্পনা এটা মত হওয়া উচিত এর paste.ubuntu.com/23915379
muru
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.