2016-04-05 6 views
2

Ich versuche, ein Muster zu passen: alles, was zwischen VD= und dem ersten Auftreten von | aus einer Zeichenkette, sagen tmp, ist wie folgt:Wie erhält man ein Muster zwischen dem ersten Auftreten von zwei Zeichen in R?

tmp <- "PC=I;RS=128850544;RE=128850566;LEN=6;S1=36;S2=499.417;REP=2;VT=Ins;VD=SMO|CCDS5811.1|r.?|-|-|protein_coding:CDS:intron:insertion:intron_variant|SO:0000010:SO:0000316:SO:0000188:SO:0000667:SO:0001627;VC=intronic;VW=SMO|CCDS5811.1|r.?|-|-|protein_coding:CDS:intron:insertion:intron_variant|SO:0000010:SO:0000316:SO:0000188:SO:0000667:SO:0001627" 

gene <- sub("^.*VD=([A-Za-z0-9]+)[|].*", "\\1", tmp) 
gene 
# [1] "SMO" 

Aber wenn es keine VD= oder | im String , packt er die ganze Reihe:

tmp <- "PC=D;RS=72450731;RE=72450735;LEN=1;S1=72;S2=802.939;REP=3;VT=Del" 

gene <- sub("^.*VD=([A-Za-z0-9]+)[|].*", "\\1", tmp) 
gene 
# [1] "PC=D;RS=72450731;RE=72450735;LEN=1;S1=72;S2=802.939;REP=3;VT=Del" 

ich verstehe nicht, warum es die gesamte Zeichenfolge statt NA auch greifen, wenn es keine VD= oder | Zeichen vorhanden. Gibt es eine Möglichkeit, ein Muster zwischen dem ersten Auftreten von zwei Zeichen zu erfassen und es zu drucken oder NA zu drucken, wenn das Muster nicht gefunden wird.

Jede Hilfe würde sehr geschätzt werden.

Danke!

+0

zuerst 'match' und dann' greifen' – rock321987

+2

'sub' /' gsub' greifen nichts, sie ** ersetzen **, und es gibt nichts in Ihrem 2. Fall ** zu ** ersetzen – eddi

+0

verwenden ' Regmatches/Regexpr' oder besser noch verwenden Sie 'striadr :: str_extract' oder Freunde – eddi

Antwort

4

Ihre Regex scheint ziemlich kompliziert für die Aufgabe. Mit einfachen Regex wie folgt

Regex:VD=([^|]+) wäre ausreichend. Verwenden Sie \\1, um Rückverweis zu geben.

Erläuterung:([^|]+) passt alles von VD= bis zum ersten | angetroffen wird.

Regex101 Demo

tmp <- c("PC=D;RS=72450731;RE=72450735;LEN=1;S1=72;S2=802.939;REP=3;VT=Del", "PC=I;RS=128850544;RE=128850566;LEN=6;S1=36;S2=499.417;REP=2;VT=Ins;VD=SMO|CCDS5811.1|r.?|-|-|protein_coding:CDS:intron:insertion:intron_variant|SO:0000010:SO:0000316:SO:0000188:SO:0000667:SO:0001627;VC=intronic;VW=SMO|CCDS5811.1|r.?|-|-|protein_coding:CDS:intron:insertion:intron_variant|SO:0000010:SO:0000316:SO:0000188:SO:0000667:SO:0001627") 
gsub('VD=([^|]+)|.', '\\1', tmp) 
# [1] "" "SMO" 
+0

'Op's' Sorge ging nicht über Regex obwohl – rock321987

+0

was genau macht Sie denken, dass OP nicht die Regex sie wollen? Das macht einen * Unterschied * von OP, und ist nicht nur eine Vereinfachung – eddi

+0

@ rock321987: Ja, aber OP verwendet ziemlich komplizierten Weg, um diese Aufgabe zu erreichen, und ich schlage eine vereinfachte Version vor. Einfach nur hilfreich sein. Wenn nur der Zweck keine direkte Lösung bieten würde, dann wäre nur eine Lösung für jede Frage wirklich hilfreich. –

1

Es sieht für mich wie Sie effektiv sind versucht, eine Multi-Level-getrennte Zeichenfolge zu analysieren. Ich empfehle nicht, eine einzelne Regex zu verwenden, um die gewünschten Informationen zu extrahieren, sondern eine strengere schrittweise Aufgliederung der Elemente der Syntax zu verwenden.

Erstens können Sie auf Semikolon teilen Sie die Top-Level-Stücke zu erhalten, wie Variablenzuweisungen aussehen:

tmp <- 'PC=I;RS=128850544;RE=128850566;LEN=6;S1=36;S2=499.417;REP=2;VT=Ins;VD=SMO|CCDS5811.1|r.?|-|-|protein_coding:CDS:intron:insertion:intron_variant|SO:0000010:SO:0000316:SO:0000188:SO:0000667:SO:0001627;VC=intronic;VW=SMO|CCDS5811.1|r.?|-|-|protein_coding:CDS:intron:insertion:intron_variant|SO:0000010:SO:0000316:SO:0000188:SO:0000667:SO:0001627'; 
specs <- strsplit(fixed=T,tmp,';')[[1L]]; 
specs; 
## [1] "PC=I" 
## [2] "RS=128850544" 
## [3] "RE=128850566" 
## [4] "LEN=6" 
## [5] "S1=36" 
## [6] "S2=499.417" 
## [7] "REP=2" 
## [8] "VT=Ins" 
## [9] "VD=SMO|CCDS5811.1|r.?|-|-|protein_coding:CDS:intron:insertion:intron_variant|SO:0000010:SO:0000316:SO:0000188:SO:0000667:SO:0001627" 
## [10] "VC=intronic" 
## [11] "VW=SMO|CCDS5811.1|r.?|-|-|protein_coding:CDS:intron:insertion:intron_variant|SO:0000010:SO:0000316:SO:0000188:SO:0000667:SO:0001627" 

Weiter Sie für die linke Seite von Interesse suchen, nur das erste Vorkommen Extrahieren (falls es sind mehrere Ursachen):

vdspec <- grep(perl=T,value=T,'^VD=',specs)[1L]; 
vdspec; 
## [1] "VD=SMO|CCDS5811.1|r.?|-|-|protein_coding:CDS:intron:insertion:intron_variant|SO:0000010:SO:0000316:SO:0000188:SO:0000667:SO:0001627" 

Sie können in die RHS Drilldown und dann aufgeteilt, dass in das Rohr getrennte Felder:

vd <- sub(perl=T,'^VD=','',vdspec); 
vd; 
## [1] "SMO|CCDS5811.1|r.?|-|-|protein_coding:CDS:intron:insertion:intron_variant|SO:0000010:SO:0000316:SO:0000188:SO:0000667:SO:0001627" 
vdfields <- strsplit(fixed=T,vd,'|')[[1L]]; 
vdfields; 
## [1] "SMO" 
## [2] "CCDS5811.1" 
## [3] "r.?" 
## [4] "-" 
## [5] "-" 
## [6] "protein_coding:CDS:intron:insertion:intron_variant" 
## [7] "SO:0000010:SO:0000316:SO:0000188:SO:0000667:SO:0001627" 

Jetzt können Sie leicht den Wert erhalten Sie suchen:

vdfields[1L]; 
## [1] "SMO" 

Wenn Ihr Ziel LHS nicht überein, werden Sie NA vom grep()[1L] Anruf erhalten:

xxspec <- grep(perl=T,value=T,'^XX=',specs)[1L]; 
xxspec; 
## [1] NA 

Sie also kann auf das Ergebnis des grep()[1L] Anrufs verzweigen, um den Fall eines fehlenden LHS zu behandeln.

Verwandte Themen