Extraire les n derniers caractères d'une chaîne dans R


271

Comment puis-je obtenir les n derniers caractères d'une chaîne dans R? Existe-t-il une fonction comme SQL's RIGHT?

Réponses:


283

Je ne suis au courant de rien dans la base R, mais il est simple de créer une fonction pour ce faire en utilisant substret nchar:

x <- "some text in a string"

substrRight <- function(x, n){
  substr(x, nchar(x)-n+1, nchar(x))
}

substrRight(x, 6)
[1] "string"

substrRight(x, 8)
[1] "a string"

Ceci est vectorisé, comme le souligne @mdsumner. Considérer:

x <- c("some text in a string", "I really need to learn how to count")
substrRight(x, 6)
[1] "string" " count"

1
Utilisez le package stringi. Cela fonctionne très bien avec les NA et tous les encodages :)
bartektartanus

Serait-il plus efficace d'éviter d'appeler nchar(x)deux fois en l'affectant à une variable locale?
Dave Jarvis

206

Si cela ne vous dérange pas d'utiliser le stringrpackage, str_subc'est pratique car vous pouvez utiliser des négatifs pour compter à rebours:

x <- "some text in a string"
str_sub(x,-6,-1)
[1] "string"

Ou, comme Max le fait remarquer dans un commentaire à cette réponse,

str_sub(x, start= -6)
[1] "string"

32
aussi, str_sub (x, start = -n) obtient n derniers caractères.
Max

2
stringr ne fonctionne pas bien avec la valeur de NA et tout l'encodage. Je recommande fortement le package stringi :)
bartektartanus

3
Je pense qu'il stringra été refait en utilisant stringiun backend, donc devrait fonctionner avec les NA, etc. maintenant.
m-dz

44

Utilisez la stri_subfonction du stringipackage. Pour obtenir la sous-chaîne de la fin, utilisez des nombres négatifs. Regardez ci-dessous pour les exemples:

stri_sub("abcde",1,3)
[1] "abc"
stri_sub("abcde",1,1)
[1] "a"
stri_sub("abcde",-3,-1)
[1] "cde"

Vous pouvez installer ce paquet depuis github: https://github.com/Rexamine/stringi

Il est disponible sur CRAN maintenant, tapez simplement

install.packages("stringi")

pour installer ce package.


20
str = 'This is an example'
n = 7
result = substr(str,(nchar(str)+1)-n,nchar(str))
print(result)

> [1] "example"
> 

12

Une autre façon assez simple consiste à utiliser des expressions régulières et sub:

sub('.*(?=.$)', '', string, perl=T)

Donc, "débarrassez-vous de tout suivi d'un seul personnage". Pour saisir plus de caractères à la fin, ajoutez autant de points dans l'assertion lookahead:

sub('.*(?=.{2}$)', '', string, perl=T)

.{2}signifie .., ou "deux caractères quelconques", ce qui signifie "se débarrasser de tout suivi de deux caractères".

sub('.*(?=.{3}$)', '', string, perl=T)

pour trois caractères, etc. Vous pouvez définir le nombre de caractères à saisir avec une variable, mais vous devrez définir la pastevaleur de la variable dans la chaîne d'expression régulière:

n = 3
sub(paste('.+(?=.{', n, '})', sep=''), '', string, perl=T)

2
Pour éviter toutes les anticipations, etc., vous pouvez simplement le faireregmatches(x, regexpr(".{6}$", x))
courrier électronique du

10

MISE À JOUR : comme indiqué par mdsumner , le code d'origine est déjà vectorisé parce que substr l'est. Aurait dû être plus prudent.

Et si vous voulez une version vectorisée (basée sur le code d' Andrie )

substrRight <- function(x, n){
  sapply(x, function(xx)
         substr(xx, (nchar(xx)-n+1), nchar(xx))
         )
}

> substrRight(c("12345","ABCDE"),2)
12345 ABCDE
 "45"  "DE"

Notez que je l' ai changé (nchar(x)-n)pour (nchar(x)-n+1)obtenir des ncaractères.


Je pense que tu veux dire " (nchar(x)-n)à (nchar(x)-n+1)"
Xu Wang

8

Une solution de base R simple utilisant la substring()fonction (qui savait que cette fonction existait même?):

RIGHT = function(x,n){
  substring(x,nchar(x)-n+1)
}

Cela profite essentiellement d'être en substr()dessous mais a une valeur finale par défaut de 1 000 000.

Exemples:

> RIGHT('Hello World!',2)
[1] "d!"
> RIGHT('Hello World!',8)
[1] "o World!"

6

Une alternative à substrest de diviser la chaîne en une liste de caractères uniques et de traiter ce qui:

N <- 2
sapply(strsplit(x, ""), function(x, n) paste(tail(x, n), collapse = ""), N)

6
Je sens un brassage de bataille system.time () :-)
Carl Witthoft

4

J'utilise substraussi, mais d'une manière différente. Je veux extraire les 6 derniers caractères de "Donnez-moi votre nourriture." Voici les étapes:

(1) Divisez les caractères

splits <- strsplit("Give me your food.", split = "")

(2) Extraire les 6 derniers caractères

tail(splits[[1]], n=6)

Production:

[1] " " "f" "o" "o" "d" "."

Chacun des personnages est accessible par splits[[1]][x], où x est compris entre 1 et 6.


3

quelqu'un utilise avant une solution similaire à la mienne, mais je trouve plus facile de penser comme ci-dessous:

> text<-"some text in a string" # we want to have only the last word "string" with 6 letter
> n<-5 #as the last character will be counted with nchar(), here we discount 1
> substr(x=text,start=nchar(text)-n,stop=nchar(text))

Cela apportera les derniers caractères comme vous le souhaitez.


3

Essaye ça:

x <- "some text in a string"
n <- 5
substr(x, nchar(x)-n, nchar(x))

Il devrait donner:

[1] "string"

1

J'ai utilisé le code suivant pour obtenir le dernier caractère d'une chaîne.

    substr(output, nchar(stringOfInterest), nchar(stringOfInterest))

Vous pouvez jouer avec le nchar (stringOfInterest) pour comprendre comment obtenir les derniers caractères.


0

Une petite modification sur la solution @Andrie donne également le complément:

substrR <- function(x, n) { 
  if(n > 0) substr(x, (nchar(x)-n+1), nchar(x)) else substr(x, 1, (nchar(x)+n))
}
x <- "moSvmC20F.5.rda"
substrR(x,-4)
[1] "moSvmC20F.5"

Voilà ce que je cherchais. Et il invite sur le côté gauche:

substrL <- function(x, n){ 
  if(n > 0) substr(x, 1, n) else substr(x, -n+1, nchar(x))
}
substrL(substrR(x,-4),-2)
[1] "SvmC20F.5"

0

Juste au cas où une gamme de caractères doit être choisie:

# For example, to get the date part from the string

substrRightRange <- function(x, m, n){substr(x, nchar(x)-m+1, nchar(x)-m+n)}

value <- "REGNDATE:20170526RN" 
substrRightRange(value, 10, 8)

[1] "20170526"
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.