2013-09-04 14 views
12

capture groups (parantez) ve bir dize içeren düzenli bir ifade verildiğinde, yakalama grupları ile eşleşen alt dizeleri, yani elde edebilirim, örneğin "\ 1", " \ 2" ?Ekstraksiyon yakalama grubu normal ifadelerden eşleşiyor mu? (veya: gregexec nerede?)

Örnek:

s <- "xy1234wz98xy567" 

r <- "xy(\\d+)" 

İstenilen sonuç: "xy" öncesinde regex yakalama basamak dikkate

[1] "1234" "567" 

İlk girişimi: gregexpr: Ben istediğini değil

regmatches(s,gregexpr(r,s)) 
#[[1]] 
#[1] "xy1234" "xy567" 

Çünkü tüm desenle eşleşen alt dizeleri döndürür.

İkinci deneyin: regexec:

regmatches(s,regexec("xy(\\d+)",s)) 
#[[1]] 
#[1] "xy1234" "1234" 

değil o sadece Tüm örneğin ve yakalama grubu için eşleştirme Birinci oluşumu döndürdüğü için ne istiyorum. regexpr uzanır regexecgregexpr olarak uzanan gregexec işlevi varsa

, benim sorunum çözülmüş olurdu.

Yani soru şudur: rasgele bir normal ifadede yakalama gruplarını eşleştiren tüm alt dizeleri (veya yukarıdaki örneklerde olduğu gibi regmatches geçirilebilen dizinler) nasıl alınır?

Not: Yukarıda verilen r için desen sadece aptalca bir örnektir, keyfi kalmalıdır. Burada baz bunu hakkında emin değil, ama

cevap

11

ihtiyaçlarınız için bir paket var: Ayrıca stringr kullanmadan bunu başarmak böylece

library(stringr) 

str_match_all(s, r) 
#[[1]] 
#  [,1]  [,2] 
#[1,] "xy1234" "1234" 
#[2,] "xy567" "567" 

Birçok stringr işlevleri, baz R paralellikler vardır. gsubfn package yılında

sapply(regmatches(s,gregexpr(r,s))[[1]], function(m) regmatches(m,regexec(r,m))) 
+1

Bu tam da ihtiyacım olan şey. Kaynağını kontrol edeceğim. Bunun temel bir görev olduğu göz önüne alındığında, baz R'de bir çözümün (ya da olması gerektiğine) inanıyorum. –

+1

Sadece "lapply" ve "regexec" (akıllıca olsa) kullanır ... Sadece şunu yazın: 'str_match_all' ve 'str_match' bunu görmek için ... – Arun

8

strapplyc bunu yapmaz:

Örneğin, burada yukarıdaki baz R kullanarak çalışır, nasıl basitleştirilmiş versiyonu

> library(gsubfn) 
> 
> strapplyc(s, r) 
[[1]] 
[1] "1234" "567" 

ek bilgiler ve örnekler için ?strapplyc deneyin.

ilgili fonksiyonları

)strapplyc bir genelleme aynı paket içinde strapply olup. Her bir eşleşmenin yakalanan kısımlarını giren ve fonksiyonun çıktısını veren bir fonksiyon alır. İşlev c olduğunda, strapplyc'a düşer.Örneğin, sayısal olarak sonuç isteyen varsayalım:

> strapply(s, r, as.numeric) 
[[1]] 
[1] 1234 567 

2)gsubfn aynı paket içinde ilgili başka bir fonksiyonudur. Değiştirme dizgisi bir yedek işlev (veya bir yedek liste veya bir yedek proto nesnesi) dışında gsub gibidir. Değiştirme işlevi, yakalanan kısımları girer ve değiştirmeyi çıkarır. Değiştirme, eşleşmeyi giriş dizesinde değiştirir. Formül kullanılırsa, bu örnekte olduğu gibi, formülün sağ tarafı işlev gövdesi olarak kabul edilir. Bu örnekte, eşleştirmeyi XY{#} ile değiştiriyoruz, burada # eşleştirilmiş giriş numarasının iki katıdır.

> gsubfn(r, ~ paste0("XY{", 2 * as.numeric(x), "}"), s) 
[1] "XY{2468}wz98XY{1134}" 

GÜNCELLEME: Eklendi strapply ve gsubfn örnekleri.

+0

Bu harika. Bir soru: 'stringr :: str_match_all' gibi bir döngüde' strapplyc' 'regexec’i çağırır mı? –

+0

'strapplyc, tcl'de (bir dize işleme dili) yazılmış temel kodu çok büyük dizeleri ve hızı işlemek için etkinleştirir ('engine =' argümanı farklı bir motor belirtmedikçe). Detaylar için '? Strapplyc''' e bakınız. –

+0

Bu cevap için çok teşekkür ederim. Eddi'yi kabul ettim çünkü önce doğru ve cevap verdi. –

12

Bir temel R çözümü için,ve regmatches() ile ayıklanan dizeleri işlemeyi bitirmek için gsub() kullanıyor musunuz?

s <- "xy1234wz98xy567" 
r <- "xy(\\d+)" 

gsub(r, "\\1", regmatches(s,gregexpr(r,s))[[1]]) 
# [1] "1234" "567" 
+0

İyi numara, ama yakalama grubu bir bakışta (örneğin, perl = TRUE') ise, başarısız olabilir. –

+0

@ Ferdinand.kraft - Bir örnek verebilir misiniz? Göz atmaların kaçırılmadığını düşünüyorum, bu yüzden ne demek istediğini göremiyorum. –

+0

Bunu düşünün: "r <-" xy (? = (\\ d +)) "; gsub (r, "\\ 1", regmatches (s, gregexpr (r, s, perl = TRUE)) [[1]], perl = TRUE); gsub (r, "\\ 1", s, perl = TRUE) ". 'Gsub' (tek başına) '\ 1’deki basamakları geri yükleyebileceğine dikkat edin. –

İlgili konular