Grep'in ps sonuçlarında görünmesini nasıl önleyebilirim?


304

Var olmayan bir işlemi ararken, örneğin

$ ps aux | grep fnord                          
wayne    15745  0.0  0.0  13580   928 pts/6    S+   03:58   0:00 grep fnord

Açıkçası grep umrumda değil - bu pssüreci aramak kadar mantıklı !

Grep'in sonuçlarda görünmesini nasıl önleyebilirim?


28
Bir işlemin sadece PID'sine ihtiyacınız varsa ps aux |grep, pgrep(veya pgrep -f) ile değiştirebilirsiniz .
jofel

6
Serverfault ve Superuser'da aynı soru .
Thor

Bu çıkış okunaklı mı? fnord running adında bir program yok gibi görünüyor ...
acolyte,

4
@acolyte, bu tam da bu - ama grep içine çıkış boru çünkü, grep (çıkışında bekleyen çalıştıran ps auxherhalde,). Yani soru önlemek için nasıl grep fnordaçıkçası ben ilgilenmiyorum çünkü çalışan bir işlem olarak gösterilmesini o biri.
Wayne Werner

2
@ akolit "fnord" çizgisini görmemeniz şaşırtıcı değildir. Görmemeniz gerekmiyor. Saklamak için 2 veya 3 dakikanız varsa, onu arayın.
Francesco

Yanıtlar:


439

Anahtarlıkta bir çözüm olduğu ortaya çıktı .

$ ps aux | grep "[f]nord"

Parantezleri mektuba koyarak ve dizgenin etrafındaki tırnak işaretlerini kullanarak, "f" ve ardından "nord" karakterini bulun.

Ancak parantezleri 'f' kalıbına yerleştirdiğiniz için şimdi ']' takip ediyor grep, sonuç listesinde görünmüyor. Neato!


26
@acolyte: ps'den gelen çıktı ile biten bir satır içerecektir grep [f]nord. Ancak, dize [f]nordnormal ifadeyle eşleşmediğinden , bu satır grep filtresi üzerinden girilmez [f]nord.
LarsH,

9
@LarsH ilginç, teşekkürler! Ben önerirdim ps aux | grep fnord | grep -v grep... ki zaten birkaç kişi tarafından önerilmiş gibi görünüyor ... lol
acolyte

5
@progo Evet, [hatta bash'ta bile alıntı yapmanız gerekiyor . fnordGeçerli dizinde adı verilen bir dosyayla deneyin .
Gilles

25
Çıktısını anlamak pseski bir numara olabilir, ama bu güvenilmez. Varsa kullanınpgrep .
Gilles

8
@ naxa Bir program aramanız fnordve adında bir programınız olduğunu hayal edin safnorde. Ya da denilen bir kullanıcı var bfnordve sonunda bütün süreçlerini öldürüyorsun. Vb
Gilles

163

Kullandığım başka bir seçenek (özellikle sadece bir işlem çalışıyorsa bakmak için) pgrep komuttur. Bu, eşleşen bir işlemi arayacak, ancak arama için bir satır çizgisi listeleymeyecektir. Hoşuma gitti, çünkü hızlı bir arama yöntemidir; herhangi bir şey düzenlemeden veya kaçmadan.

pgrep fnord

8
Onlar isteyecektir -fseçeneği daha gibi olmak ps | grep.
jordanm

@ jordanm Aslında, pgrep -fdaha çok benzeyecek ps -f | grep.
michelpm

5
-lEşleştirilen komutu göstermesini sağlayacak argüman da var.
Patrick

15
ps | grep '[f]nord'zeki ve saygıdeğer, ancak pgrep haklı .
kojiro

3
ps $(pgrep cmd) ...Pgrep seçeneği yoksa , her zaman yapabilirsiniz (ancak boş komutlar için işe yaramaz).
Maciej Piechotka

62

İdeal çözüm BriGuy tarafından sunulan çözümdür.

pgrep fnord 

Ancak bunu yapmak istemiyorsanız, grep ile eşleşen tüm satırları hariç tutabilirsiniz :

ps aux | grep -v grep | grep "fnord"

7
peki ya aradığım hat "bash bash grep bash" ise?
Sparr

1
@Sparr O zaman en iyi çözümü kullanmalısınız: pgrepya da başka bir tane bulmalısınız;)
RSFalcon7

Pgrep ile isim uzunluğu sınırına dikkat edin. Tam yol adını bulmak için -f tuşunu kullanın, aksi halde eşleşmelerinizin daha uzun isimlerle başarısız olduğunu görebilirsiniz. -Ben de maçları listelemek çok güzel
Neil McGill

25

En zarif çözüm değil ama bunu yapabilirsiniz:

$ ps aux | grep fnord | grep -v grep


Bu kötü cevap! Çünkü cümlenizde bir kelime varsa grep. Bu süreci göstermeyecek. Örneğin, bir dosyanın komut foo_grep_bar.txttarafından düzenlendiğini varsayalım nano. Yani çalışan bir süreç var: root 14908 0.0 0.0 110012 1692 pts / 3 S + Oct31 0:00 nano foo_grep_bar.txtBu cevaba göre, bu işe yaramaz: $ ps aux | grep nano | grep -v grepÇünkü dosya adınızda bir grep sözcüğü var.
Nabi KAZ

Bunu, niyeti hakkında kabul edilen cevaptan daha açık olarak kabul ediyorum ve bir dava dışında hepsinde işe yarar.
samaspin

1
gereğince superuser.com/a/409658/450260 tam hariç olmalıdır grep fnordadil değil grepyani $ ps aux | grep fnord | grep -v "grep fnord"
Davos

15

Zsh içinde grep fnord =(ps aux).

Buradaki fikir, ilk önce ps auxsonucu bir dosyaya koymak ve daha sonra grepbu dosyayı kullanmaktır . Sadece, zsh'ın “işlem değiştirme” sini kullandığımız için bir dosyamız yok.

Göstermek için deneyin

ps aux > ps.txt
grep fnord ps.txt
rm ps.txt

Sonuç aynı olmalı.

Diğer cevapların bazıları hakkında genel yorum . Bazıları karmaşık olmaktan uzak ve / veya yazmak için uzun. Bu sadece haklı olma meselesi değil, aynı zamanda kullanılabilir olması gerektiğidir. Ancak bu, bazı çözümlerin kötü olduğu anlamına gelmez; yalnızca onları kullanılabilir hale getirmek için bir mini UI içine sarılmalıdırlar.


1
Zsh'ın işlem değişimini bilmemekle birlikte, iki işlemin birbiri ardına adlandırıldığı ve paralel olmadığı kesin mi?
Paŭlo Ebermann

3
@ PaŭloEbermann: Paralel olduğu için <(command). grep grep =(ps aux)herhangi bir çizgi göstermiyor.
Maciej Piechotka

Zsh ayrıca ps'den gelen çıktıyı can eşleştirebilir. print -l ${(M)${(f)¨$(ps aux)¨}:#*fnord*}
Friartek

7
ps aux | grep $(echo fnord | sed "s/^\(.\)/[\1]/g")

3
bu bir IOCCC'ye benziyor, fakat C ^^ yerine unix komut satırı için | grep $(echo fnord)yeterli değil mi? Ayrıca sed'den "fnord" içindeki her bir karakteri kendi değerine göre aramasını ve değiştirmesini ister misiniz? ^^ tebrikler. Bahse girerim daha uzun bir tane yapabilirim, ama muhtemelen o kadar eğlenceli olmayacak ^^ ^^
Olivier Dulac

1
Yukarıdaki yorumumun tonu rahatsız edici gelebilir diye özür dilerim (ve 5 milyondan sonra düzenleyemiyorum) ... Cevabınız gerçekten neşeli bir okumaydı ve sizi kötü göstermeye çalışmıyordum. Gerçekten bilerek böyle yaptığını düşünüyorum ^^
Olivier Dulac

1
Özür dileme, cevabını okumak gerçekten eğlenceliydi (ve tam da yerinde). Ben zaten pgrep-1 dolar demek istedim;)
yPhil

3
@OlivierDulac: İlk karakteri sadece kendi değeri ile değiştirmiyor; köşeli parantez içindeki değerini bir araya getirerek yerini alır. (Bu köşeli parantezler özel değildir, gerçek anlamlıdırlar.) Temel olarak, Wayne Werner'in cevabını genelleştiriyor, böylece ilk karakterin etrafına köşeli parantez koyma işlemi yazılabilir. +1
LarsH

2
ps aux | grep '[^]]fnord'Bu jimnastikten kaçınırdı.
Stéphane Chazelas,

6

Answer Bu cevap GNU'ya özeldir . Daha genel bir çözüm için Wayne'in cevabına bakınız .

İşlemler aranıyor

Sadece fnordişlemleri arıyorsanız , -Ckomut adına göre seçmek için seçeneği kullanabilirsiniz :

ps -C fnord

Bu, BSD ve POSIX tarzı format seçenekleriyle beğeninize göre karıştırılabilir. Tam bir liste için ps man sayfasına bakınız .

Başka bir şey mi arıyorsunuz?

Bir komut adı için kesin bir aramadan daha gelişmiş bir şeye ihtiyacınız olursa, umut vermeyin! Bu hala psborunun yanında yapılabilir . Tek yapmamız gereken, süreçleri sonuçtan psdışlamayı söylemek .grep

ps -NC grep | grep 'fnord'

-C greptüm grep işlemlerini seçer -Nve seçimi olumsuzlar. Bu, komut argümanlarını, komut adının bir bölümünü veya daha karmaşık normal ifadeleri aramak için kullanılabilir.


1
Bu GNU için iyidir psancak -CPOSIX tarafından belirtilmemiştir ve BSD için tamamen farklı bir anlamı vardır
Eric Renouf

Gerçekten BSD eşdeğeri olmayan bir serseri (bu aynı zamanda bir mac üzerinde çalışmayacağı anlamına gelir). Ps -C kullanmak, bunlardan herhangi birinin en basit cevabıdır.
Christopher Hunter

3

Cevabım, 'ps' listesindeki "foobar" kelimesini aramak için verilen tipik cevabın bir çeşididir. "-A" "ps" argümanı "aux" dan daha taşınabilir, inanıyorum, ancak bu değişiklik cevapla alakasız. Tipik cevap şöyle görünür:

$ ps -A -ww | grep [f]oobar

Bunun yerine bu deseni kullanıyorum:

$ ps -A -ww | grep [^]]foobar

Asıl avantajı, bu kalıplara dayanarak komut dosyaları yazmanın daha kolay olmasıdır, çünkü statik bir dizgeyi "[^]]" aradığınız desenle birleştirirsiniz. Dizenin ilk harfini çıkarmanız, sonra köşeli parantezin arasına yerleştirmeniz ve sonra tekrar bir araya getirmeniz gerekmez. Kabuk içinde komut dosyası yazarken, aradığınız kalıbın önüne "[^]]" yapıştırmanız daha kolaydır. Bash'de dize dilimleme çirkin bir şeydir, bu yüzden varyasyonum bundan kaçınır. Bu varyasyonda, desenin lider bir sağ köşeli ayraç OLMADIĞINDAN desenle eşleştiği satırlar gösteriliyor. Köşeli parantezi hariç tutacak olan arama deseni aslında köşeli parantezi desene eklerse, o zaman hiçbir zaman kendi kendine eşleşmez.

Böylece taşınabilir bir 'psgrep' komutu aşağıdaki gibi yazabilirsiniz. Burada, Linux, OS X BSD ve diğerleri arasındaki farklar için bir miktar izin veriyorum. Bu, 'ps' sütun başlıklarını ekler, gereksinimlerime göre daha özel bir 'ps' formatı sağlar ve komut satırı argümanlarının hiçbirinin kaçırılmaması için ekstra geniş ve fazla geniş listeleme işlemlerini görüntüler. Pek çoğu kaçırılmamış. Java, Java olduğundan, genellikle işleri en kötü şekilde yapar, bu nedenle bazı java servisleri, işlem tablosunun izleyeceği izin verilen maksimum bağımsız değişkenler uzunluğunu aşar. Bunun 1024 karakter olduğuna inanıyorum. Bir işlemi başlatmak için izin verilen komut uzunluğu çok daha uzun, ancak çekirdek işlem tablosu 1K'dan daha uzun olan herhangi bir şeyin izini sürmekle uğraşmıyor. Komut başlatıldıktan sonra komut adı ve argüman listesi

psgrep ()
{
    pattern=[^]]${1};
    case "$(uname -s)" in
        Darwin)
            ps -A -ww -o pid,ppid,nice,pri,pcpu,pmem,etime,user,wchan,stat,command | grep -i -e "^[[:space:]]*PID" -e ${pattern}
        ;;
        Linux)
            ps -A -ww -o pid,ppid,tid,nice,pri,pcpu,pmem,etime,user,wchan:20,stat,command | grep -i -e "^[[:space:]]*PID" -e ${pattern}
        ;;
        *)  # other UNIX flavors get a minimalist version.
            ps -A -ww | grep -i -e ${pattern}
        ;;
    esac
}

2

Bunu yapmanın en basit kabuğu-agnostik yolu ilk önce onu bir değişkende saklamak olacaktır:

PS_OUTPUT="$(ps aux)"; echo "$PS_OUTPUT" |grep fnord

Call-out: @ EmanuelBerg'in grep fnord =(ps aux)cevabı, gerektirdiği halde, bugüne kadarki en zarif cevap zsh. Kısaca, rc dosyamın içinde bulundum, ancak değerlendirme yapılmasını engelleyen bir şartlıya rağmen, bash bu sözdiziminden şikayet ediyor.


Rc dosyalarımdan grep'in argümanını alan büyük küçük harf duyarsız bir sürüme sahibim:

psl() {
  local PS_OUTPUT="$(ps auxww)"
  echo "${PS_OUTPUT%%$'\n'*}" >&2  # title, in stderr to avoid pipes
  echo "${PS_OUTPUT#*$'\n'}" |grep -i "${@:-^}"
}

Kod yürüyüşü, kod satırı başına bir madde işareti:

  • Ayrıntılı psçıktıyı yakalayın (bir localdeğişkende, işlev döndüğünde kaybolur)
  • İlk satırı (başlık) standart hatada gösterin, böylece sonuçlar başlığın etkilenmeden filtrelenebilir. Yerine "diyor ki: $PS_OUTPUTilk satır beslemesinden sonra her şeyi al ve kaldır (regex equiv:) s/\n.*$//msg. Bu, başlığı greplememizi önlüyor
  • Ekran psher şeyi çıkışı hariç (regex eşdeğeri: İlk satırda s/^.*\n//m) ve içindekileri grep -ihiçbir argüman durumunda, (bu işlevi uzattı durumda duyarlı ve bağımsız değişkenlerin hepsi ile ^eşleştirmek için herhangi bir satırın başlangıcıyla eşleşir, herşey)

1

Belki bu sefer gerçek bir dizi kullanmanın zamanı geldi. Boruların kullanımı onu paralel yapar.

ps aux >f && grep tmpfs <f

Çirkin bir dosya olacağı için f, ama daha önce çalıştırılan bir işlemin çıktısını kullanmak istediğiniz hala sıralı işlemler için sözdizimi olmaması benim hatam değil.

Sıralı bir işlecin sözdizimi için öneri:

ps aux ||| grep tmpfs

Sıradan insanların bir akıntıyı kolayca filtreleyememeleri, elitlerin kendilerini dizilerle temel almaları için zor bir nedendir. Bilgisayarda geriye doğru bir adım olur.
Acumenus

@ ABB en.wikipedia.org/wiki/Communicating_sequential_processes , Thompson kabuğundaki sonuçlardan daha fazla operatöre sahiptir. Sıralı olan ve sonucunu çıkar çıkmaz sıradaki bir sonraki işleme ileten bir operatör olabilirdi. Ek bir operatör sağlayarak "hesaplamada geriye doğru bir adım" biraz zor görünüyor.
Anne van Rossum

Güzel bir bağlantı, fakat elbette sıralı işlem, hem işlemci hem de bellek (veya disk) kullanımında daha kötüdür - paralel işleme göre. Bu durumda, psönce tüm çıktıları saklamam gerekiyorsa grep, daha uzun süre daha fazla bellek (veya disk) kullanıyorum.
Acumenus

0

Diğerlerinin de belirttiği gibi pgrep komutu, adı ve diğer öznitelikleri temel alan işlemlerin PID (işlem kimliği) değerini döndürür. Örneğin,

pgrep -d, -u <username> <string>

adı kullanıcı tarafından çalıştırılan tüm işlemlerin virgül (,) ile sınırlandırılmış PID'lerini size verecektir <username>. Yalnızca tam eşleşmeleri döndürmek için -x anahtarını kullanmadan önce kullanabilirsiniz.

Bu işlemler hakkında daha fazla bilgi edinmek istiyorsanız (ps'deki ps seçeneklerinden çalıştırıldığı gibi), -p seçeneğini, PID'ye göre eşleşen ps ile kullanabilirsiniz. Yani, örneğin,

ps up $(pgrep -d, -u <username> <string>)

pgrep komutu ile eşleşen tüm PID'ler hakkında ayrıntılı bilgi verecektir.


pspgrepboş bir küme döndürürse başarısız olur . Sizinkine dayanan ve bu konuyu ele almaya çalışan bir cevabım var .
Acumenus

0

Prosesin ssh-agentPID'sini göstermeden kullanıcı adı için PID'yi bulmak için basit bir örnek grep:

ps xu | grep "${USER}.*[ ]/usr/bin/ssh-agent" | awk '{print $1 $2;}'

Örneğin ssh-agentmevcut kullanıcı için öldürmek istiyorsanız, aşağıdaki komutu kullanabilirsiniz:

kill `ps xu | grep "${USER}.*[ ]/usr/bin/ssh-agent" | awk '{print $2;}'`

Kullanışlı bir takma ad oluşturmak için ~ / .bashrc veya ~ / .zshrc dosyanıza aşağıdaki kodu ekleyin:

function function1 () {
    ps xu | grep "$1.*$2" | awk '{print $1" "$2" "$11;}'
}
alias mygrep="function1"

Ve buradaki diğer adını kullanmak, herkesi düzenli ifadeleri öğrenmeye zorlayan örneklerdir:

. /etc/profile #to make alias usable
mygrep ${USER} ${PROCESS_PATH}
mygrep ${USER} "[f]nord"
mygrep "[f]nord"
mygrep ".*[s]shd"

PS Bu komutları yalnızca Ubuntu ve Gentoo'da test ettim.


(1) Soru, kullanıcının kendi işlemlerinden birini aradığını söylemez - kullanıcı aradığı işlemin sahibini tanımıyor olabilir. (2) Bu cevabın ne kadar süslü olduğu söylenirse, yine de başarısız olur "${USER}.* /usr/bin/ssh-agent". İşe yarıyor çünkü sen söyledin [ ]; yani, sadece kabul edilen cevabın mekanizmasını kullanıyorsunuz. Sen de olabilirsin grep "[s]sh-agent".
G-Man

Haklısın. (1) Arada sırada kendimi bu sayfayla karşı karşıya bulduğum için faydalı olabilecek şeyleri paylaştım (2) Evet Kabul edilen yanıtta olduğu gibi düzenli ifadeler kullandım. (3) Cevabımı daha iyi olduğu gibi kabul edilebilecek şekilde güncelledim, ancak sağlanan kullanıcı adı ile veya kullanıcı adında nasıl kullanılacağını ve takma adını kullandım. (4) Ayrıca, gerekli olmamakla birlikte, fonksiyonun nasıl tanımlanacağı gösterilmiştir; ancak, $ 1 ve $ 2 çakışmadığı için ilginç bir şekilde çalışır. Thx # G-Man
Constantin Zagorsky

-1

Kolayca yapabilirsiniz, sadece sizin .bashrc gibi bir ALIAS tanımlayarak :

alias grep='grep -v grep | grep'

Kimin oy kullandığı veya neden seçildiğinden emin değil, ancak bu, pgrep'in kullanmadığı ps'nin tam kullanımını kullanmanıza izin verir.
opticyclic

Sadece bu yanlışlıkla diğer grep işlemlerini dışlar; aynı zamanda grepdiğer durumlarda kullanımı da bozar . Dene echo I love grep | grep love.
torosos

@trosos Neredeyse 11 yıldır * karıştırıyorum .. ve bu modeli hiç kullanmamıştım ... belki gelecek yıl olsa da - kim bilir.
a20

-1

-X (kesin eşleme) seçeneğini kullanmak benim için çalıştı. -F (full komut satırı) ile birleştirdim, böylece işlemimi tam olarak eşleştirebilirim:

pgrep -x -f "path_i_used_when_starting/cmd params_i_used"

Araba süren aşağı oylama yapan kimse kendini açıklar mı? Bu benim için yıllarca başarısız olmadan bu sorunu çözmek için çalışıyor.
moodboom
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.