File kumpulan: Temukan apakah substring dalam string (bukan dalam file)


208

Dalam file batch, saya punya string abcdefg. Saya ingin memeriksa apakahbcd ada dalam string.

Sayangnya sepertinya semua solusi yang saya temukan mencari file untuk substring, bukan string untuk substring.

Apakah ada solusi mudah untuk ini?


5
BTW, biasanya baik Windowsdan cmd atau itu ms-dos. MSDOS belum bagian dari Windows untuk lama waktu.
paxdiablo

Jawaban:


288

Ya, Anda dapat menggunakan substitusi dan memeriksa string asli:

if not x%str1:bcd=%==x%str1% echo It contains bcd

The %str1:bcd=%bit akan mengganti bcddalam str1dengan string kosong, sehingga berbeda dari aslinya.

Jika aslinya tidak mengandung bcdstring di dalamnya, versi yang diubah akan identik.

Pengujian dengan skrip berikut akan menunjukkannya dalam tindakan:

@setlocal enableextensions enabledelayedexpansion
@echo off
set str1=%1
if not x%str1:bcd=%==x%str1% echo It contains bcd
endlocal

Dan hasil dari berbagai proses:

c:\testarea> testprog hello

c:\testarea> testprog abcdef
It contains bcd

c:\testarea> testprog bcd
It contains bcd

Beberapa catatan:

  • The ifpernyataan adalah daging dari solusi ini, segala sesuatu yang lain adalah dukungan hal.
  • The xsebelum kedua belah pihak kesetaraan ini adalah untuk memastikan bahwa string bcdbekerja baik-baik saja. Ini juga melindungi terhadap karakter awal "tidak patut" tertentu.

7
Jika Anda mencari cara melakukan penggantian string dalam loop FOR: stackoverflow.com/a/6310580/623622
Czarek Tomczak

60
Ini bagus, tetapi saya berjuang untuk membuatnya berfungsi ketika nilai pencariannya tidak konstan (seperti bcd) tetapi sebagai variabel. Setelah banyak waktu akhirnya saya menemukan jawabannya. Dengan asumsi searchVal telah dinyatakan, "x! Str1:% searchVal% =!" == "x% str1%"
Gary Brunton

7
@ Gary, karena itu bukan salah satu persyaratan dari pertanyaan ini, Anda mungkin harus mengajukan pertanyaan yang berbeda, mungkin menghubungkan kembali ke pertanyaan ini sebagai referensi. Tidak ada kekurangan orang yang mau membantu. Bahkan, Anda masih harus mengajukan pertanyaan itu dan menjawabnya sendiri (sekarang setelah Anda mengetahuinya) sehingga akan bermanfaat bagi pencari di masa depan. Menjawab sendiri dianggap dapat diterima.
paxdiablo

6
Solusi yang sangat baik, tetapi Anda harus menyertakan tanda kutip ganda atau tidak akan bekerja dengan variabel yang memiliki spasi dalam nilainya, misalnya: jika tidak "x% str1: bcd =%" == "x% str1%" echo It mengandung bcd
Helge Klein

4
"'= str1 tidak terduga pada saat ini"
Berit Larsen

104

Anda dapat menyalurkan string sumber ke findstrdan memeriksa nilai ERRORLEVELuntuk melihat apakah string pola ditemukan. Nilai nol menunjukkan keberhasilan dan pola ditemukan. Berikut ini sebuah contoh:

::
: Y.CMD - Test if pattern in string
: P1 - the pattern
: P2 - the string to check
::
@echo off

echo.%2 | findstr /C:"%1" 1>nul

if errorlevel 1 (
  echo. got one - pattern not found
) ELSE (
  echo. got zero - found pattern
)

Ketika ini dijalankan di CMD.EXE, kita mendapatkan:

C:\DemoDev>y pqrs "abc def pqr 123"
 got one - pattern not found

C:\DemoDev>y pqr "abc def pqr 123" 
 got zero - found pattern

"FINDSTR: Argumen hilang setelah / C. punya satu - pola tidak ditemukan"
Berit Larsen

47

Saya biasanya melakukan sesuatu seperti ini:

Echo.%1 | findstr /C:"%2">nul && (
    REM TRUE
) || (
    REM FALSE
)

Contoh:

Echo.Hello world | findstr /C:"world">nul && (
    Echo.TRUE
) || (
    Echo.FALSE
)

Echo.Hello world | findstr /C:"World">nul && (Echo.TRUE) || (Echo.FALSE)

Keluaran:

TRUE
FALSE

Saya tidak tahu apakah ini cara terbaik.


Saya perlu menemukan dan membandingkan nama file secara rekursif. Ini adalah satu-satunya solusi yang bekerja untuk saya juga! Sangat berguna dan sangat sederhana.
SirJames

24

Untuk kompatibilitas dan kemudahan penggunaan, sering kali lebih baik menggunakan FIND untuk melakukan ini.

Anda juga harus mempertimbangkan apakah Anda ingin mencocokkan case sensitif atau case sensitif.

Metode dengan 78 poin (saya yakin saya merujuk pada posting paxdiablo) hanya akan cocok dengan Case Sensitive, jadi Anda harus meletakkan cek terpisah untuk setiap variasi kasus untuk setiap kemungkinan iterasi yang mungkin ingin Anda cocokkan.

(Betapa merepotkan! Hanya 3 huruf yang berarti 9 tes berbeda untuk menyelesaikan cek!)

Selain itu, sering kali lebih baik untuk mencocokkan output perintah, variabel dalam satu lingkaran, atau nilai variabel pointer di batch / CMD Anda yang tidak lurus ke depan.

Untuk alasan ini, ini adalah metodologi alternatif yang lebih disukai:

Gunakan: Temukan [/ I] [/ V] "Karakter yang Cocok"

[/ I] (Huruf peka) [/ V] (TIDAK boleh mengandung karakter)

Sebagai Baris Tunggal:

ECHO.%Variable% | FIND /I "ABC">Nul && ( Echo.Found "ABC" ) || ( Echo.Did not find "ABC" )

Multi-line:

ECHO.%Variable%| FIND /I "ABC">Nul && ( 
  Echo.Found "ABC"
) || (
  Echo.Did not find "ABC"
)

Seperti yang disebutkan ini bagus untuk hal-hal yang tidak ada dalam variabel yang memungkinkan penggantian string juga:

FOR %A IN (
  "Some long string with Spaces does not contain the expected string"
  oihu AljB
  lojkAbCk
  Something_Else
 "Going to evaluate this entire string for ABC as well!"
) DO (
  ECHO.%~A| FIND /I "ABC">Nul && (
    Echo.Found "ABC" in "%A"
  ) || ( Echo.Did not find "ABC" )
)

Output From a command:

    NLTest | FIND /I "ABC">Nul && ( Echo.Found "ABC" ) || ( Echo.Did not find "ABC" )

As you can see this is the superior way to handle the check for multiple reasons.

untuk masalah sensitivitas kasus, Anda dapat menggunakan setlocal EnableExtensionskemudian IF /Iuntuk melakukan perbandingan kasus sensitif.
cychoi

1
Itu sebenarnya bukan pilihan karena Anda masih perlu mengisolasi karakter untuk Perbandingan "JIKA". JIKA tidak akan cocok dengan "Suka" Ketentuan sebagai OP dan solusi khusus yang saya jawab mencari.,
Ben Personick

Hai Ben, Tolong jangan merujuk jawaban lain dengan jumlah poin yang mereka miliki. Itu kemungkinan akan berubah. Harap perbarui jawaban Anda dengan merujuk pada jawaban lain dengan nama penulis jawaban itu, atau dengan frasa singkat yang menggambarkan teknik yang digunakan dalam jawaban itu.
phonetagger

Hai Tagger Telepon, itu akan menjadi komentar yang bermanfaat tiga tahun lalu ketika saya menulis posting asli, namun ketika Anda menyebutkan nilai poin semua telah berubah. Saya tidak lagi ingat posting mana yang saya maksudkan, dan saya tidak akan merujuknya dengan nilai poin hari ini. Bagaimanapun, terima kasih.
Ben Personick

Saya melihat sekeliling dan saya percaya saya merujuk paxdiablo, jadi saya telah mengubah teks untuk menunjukkan itu.
Ben Personick

10

Jika Anda mendeteksi keberadaan, berikut adalah solusi termudah:

SET STRING=F00BAH
SET SUBSTRING=F00
ECHO %STRING% | FINDSTR /C:"%SUBSTRING%" >nul & IF ERRORLEVEL 1 (ECHO CASE TRUE) else (ECHO CASE FALSE)

Ini berfungsi baik untuk menjatuhkan output perintah windows ke dalam variabel boolean. Ganti gema dengan perintah yang ingin Anda jalankan. Anda juga dapat merangkai Findstr bersama untuk lebih lanjut memenuhi syarat pernyataan menggunakan pipa. EG untuk Kontrol Layanan (SC.exe)

SC QUERY WUAUSERV | findstr /C:"STATE" | FINDSTR /C:"RUNNING" & IF ERRORLEVEL 1 (ECHO case True) else (ECHO CASE FALSE)

Yang satu mengevaluasi output dari SC Query untuk layanan pembaruan windows yang keluar sebagai teks multiline, menemukan baris yang berisi "status" kemudian menemukan jika kata "running" muncul pada baris itu, dan mengatur tingkat kesalahan sesuai.


6
Anda memiliki Pernyataan IF Anda Mundur .. Melihat yang asli dengan abcdefg dan Anda flip-flop logika Anda. Berhasil. Cara Anda memilikinya, tidak. SET STRING=abcdefgh SET SUBSTRING=bcd ECHO %STRING% | FINDSTR /C:"%SUBSTRING%" >nul & IF ERRORLEVEL 1 (ECHO CASE FALSE) else (ECHO CASE TRUE)
Leptonator

2
+1 diberikan karena @Leptonator benar dengan logika terbalik. Ini adalah solusi yang sederhana dan mudah digunakan.
Laryx Decidua

2

Saya mungkin datang agak terlambat dengan jawaban ini, tetapi jawaban yang diterima hanya berfungsi untuk memeriksa apakah "hard-coded string" adalah bagian dari string pencarian.

Untuk pencarian dinamis, Anda harus melakukan ini:

SET searchString=abcd1234
SET key=cd123

CALL SET keyRemoved=%%searchString:%key%=%%

IF NOT "x%keyRemoved%"=="x%searchString%" (
    ECHO Contains.
)

Catatan: Anda bisa menggunakan dua variabel sebagai argumen.


1

Jawaban yang lebih baik ada di sini :

set "i=hello " world"
set i|find """" >nul && echo contains || echo not_contains

Dalam pertanyaan yang Anda tautkan menggunakan SET menyelesaikan kebutuhan spesifik dan unik, jadi penting untuk menyebutkan "SET". Namun, tampaknya tidak menambah apa pun pada diskusi saat ini, karena metode pemipaan perintah ke perintah FIND dan pengujian hasilnya sudah disediakan
Ben Personick


0

Solusi yang mencari file untuk substring juga dapat mencari string , misalnya. findatau findstr.
Dalam kasus Anda, solusi mudahnya adalah menyalurkan string ke dalam perintah alih-alih memberikan nama file misalnya.

string case-sensitive:
echo "abcdefg" | find "bcd"

abaikan case string:
echo "abcdefg" | find /I "bcd"

JIKA tidak ditemukan kecocokan, Anda akan mendapatkan respons baris kosong pada CMD dan% ERRORLEVEL% ditetapkan ke 1

Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.