2016-03-29 10 views
2

Ich möchte den Weg kennen, den Vektor als Ganzes zu vergleichen. Ich habe zwei Vektoren a,bWie Vektorelemente als Ganzes übereinstimmen

a <- c(5,1,2,6,3,4,8) 
b <- c(1,2,3) 

Ich kenne ein paar Möglichkeiten, um die Vektorelemente wie

match(b,a) 
#[1] 2 3 5 

b%in%a 
#[1] TRUE TRUE TRUE 

Auf match() i die Lage der einzelnen Vektorelemente erhalten entsprechen und für %in% i logische erhalten für einzelne Vektorelemente . Aber ich suche den gesamten Vektor b mit a auf einmal. Es sollte nicht mit den einzelnen Elementen übereinstimmen, sondern mit dem gesamten Vektor und den Ort erhalten, an dem das Spiel beginnt.

gewünschte Ausgabe:

In der obigen Vektoren Übereinstimmung gefunden wird nicht, weil ich für den gesamten Vektor nicht die einzelnen Vektor Artikel suchen.

+0

@Henrik testen . Danke, dass Sie ein mögliches Duplikat gefunden haben. Ich schaue, vielleicht kann es hilfreich sein. –

+0

@rawr Vielen Dank für die Führung des Links. Die Frage ist bereits geschlossen und der Link scheint nicht verwandt zu sein. Der Link von 'Henrik' früher, später gelöscht funktioniert gut. Danke allen !! –

+0

@rawr !!. Ich beziehe mich auf den Link oben, nicht auf Ihren Link. Bitte lösche den Link nicht. –

Antwort

0

Sie könnten immer brute zwingen, nur die Vektoren Element für Element durchlaufen.

a <- c(5,1,2,6,3,4,8) 
b <- c(1,2,3) 

matchr <- function(a,b){ 

    # First, loop through the a vector 
    for(i in 1:(length(a)-length(b))){ 

     pos <- FALSE 

     # Next loop through the b vector, 
     for(j in 1:length(b)){ 

      # as we're looping through b, check if each element matches the corresponding part of the a vector we're currently at. 
      if(a[i+j-1] == b[j]){ 
       pos <- TRUE 
      } else{ 
       pos <- FALSE 
       break 
      } 
     } 

     # if all the elements match, return where we are in the a vector 
     if(pos == TRUE){ 
      return(i) 
     } 
    } 
    # if we finish the a vector and never got a match, return no match. 
    return("No match") 
} 

matchr(a,b) 
[1] "No match" 

d <- c(7,5,4,2,1,2,3,8,5) 

matchr(d,b) 
[1] 5 

e <- c(2,3,8) 

matchr(d,e) 
[1] 6 

Wenn Ihr reeller Vektor ist viel größer, können Sie die Funktion über matchr <- compiler::cmpfun(matchr) Kompilieren betrachten oder mit RCPP neu zu schreiben.

Edit: up a Liste Eine andere Art und Weise

eine Liste mit Ihren a Vektor Split Stellen in length(b) Größe Vektoren, dann testen, ob list(b) im Split ist:

matchr2 <- function(a){ 
    m <- list() 
    for(i in 1:(length(a)-length(b))){ 
     m[[i]] <- c(a[i : (length(b) + i - 1)]) 
    } 
    m 
} 

mlist <- matchr2(a) 

list(b) %in% mlist 
[1] FALSE 

mlist <- matchr2(d) 

list(b) %in% mlist 
[1] TRUE 

wieder, erhalten Sie erhebliche Geschwindigkeitsvorteile durch das Zusammenstellen der Funktion.

0

Ein Ansatz, mit ein paar Beispiele:

wholematch<-function(a=c(5,1,3,2,1,2,5,6,2,6),b=c(1,2,6)) 
{ 
    for(loop.a in 1:(length(a)-length(b))) 
    { 
    #pmatch gives the first occurrence of each value of b in a. To be sure of finding the consecutive matches, use pmatch starting from all the possible positions of "a" 
    wmatch<-(loop.a-1)+pmatch(b,a[loop.a:length(a)]) 
    #If at any time the number of matches is less than the length of the vector to match, we will never find a match. Return NA 
    if(length(na.omit(pmatch(b,a[loop.a:length(a)])))<length(b)) return(NA) 
    #If all indices are adjacent, return the vector of indices 
    if(max(diff(wmatch))==1) return(wmatch) #return(wmatch[1]) if you only want the start 
    } 
} 

wholematch() 
[1] NA 

wholematch(a=c(5,1,3,2,1,2,5,6,2,6),b=c(6,2,6)) 
[1] 8 9 10 
1

über Wie wenn wir die Länge überprüfen (mit na.omit) der Ausgabe von match() gegen den Vektor wir

ifelse(length(na.omit(match(b, a))) == length(b), match(b, a)[1], NA) 
#[1] 2 
#adding a new value in b so it wont match, we get 
b <- c(1, 2, 3, 9) 
ifelse(length(na.omit(match(b, a))) == length(b), match(b, a)[1], NA) 
#[1] NA