J'ai besoin d'extraire les valeurs de tension artérielle d'une note de texte qui est généralement rapportée comme un nombre plus grand, "/" sur un nombre plus petit, avec les unités mm HG (ce n'est pas une fraction, et seulement écrit comme tel). Dans les 4 exemples ci-dessous, je veux extraire 114/46, 135/67, 109/50 et 188/98 uniquement, sans espace avant ou après et placer le numéro du haut dans la colonne appelée SBP, et le numéro du bas dans une colonne appelée DBP. Merci d'avance pour votre aide.
bb <- c("PATIENT/TEST INFORMATION (m2): 1.61 m2\n BP (mm Hg): 114/46 HR 60 (bpm)", "PATIENT/TEST INFORMATION:\ 63\n Weight (lb): 100\nBSA (m2): 1.44 m2\nBP (mm Hg): 135/67 HR 75 (bpm)", "PATIENT/TEST INFORMATION:\nIndication: Coronary artery disease. Hypertension. Myocardial infarction.\nWeight (lb): 146\nBP (mm Hg): 109/50 HR (bpm)", "PATIENT/TEST INFORMATION:\nIndication: Aortic stenosis. Congestive heart failure. Shortness of breath.\nHeight: (in) 64\nWeight (lb): 165\nBSA (m2): 1.80 m2\nBP (mm Hg): 188/98 HR 140 (bpm) ") BP <- head(bb,4) dput(bb)
3 Réponses :
Vous pouvez utiliser str_match
et sélectionner des nombres qui ont /
entre
as.data.frame(do.call(rbind, strsplit(sub(".*?(\\d+/\\d+).*", "\\1", bb), "/")))
En base R, nous pouvons extraire les nombres qui suivent le modèle a / b
, divisez-les sur '/'
et formez deux colonnes.
as.data.frame(stringr::str_match(bb, "(\\d+)/(\\d+)")[, 2:3]) # X1 X2 #1 114 46 #2 135 67 #3 109 50 #4 188 98
Vous pouvez leur donner les noms de colonnes selon votre choix en utilisant setNames
ou toute autre méthode.
Merci, cela a fonctionné facilement! Existe-t-il un moyen de placer les deux nouvelles colonnes en tant que nouvelles colonnes 11 et 12 dans le dataframe d'origine? Sinon, je peux toujours lier ces deux colonnes à l'ensemble de données maître.
Vous pouvez faire cbind (df, as.data.frame ..... reste du code)
Solution de base R:
setNames(data.frame(do.call("rbind", strsplit(trimws(gsub("[[:alpha:]]|[[:punct:]][^0-9]+", "", gsub("HR.*", "", paste0("BP", lapply(strsplit(bb, "BP"), '[', 2)))), "both"), "/"))), c("SBP", "DBP"))
Merci pour votre temps et votre aide. Je l'ai essayé et j'ai aimé que les colonnes soient bien intitulées. Cependant, la trame de données a répété les deux colonnes et s'est retrouvée avec 4, deux avec les titres SBP et DBP, et deux sans aucun nom de colonne. J'ai aussi remarqué parfois que cela ajoutait des numéros supplémentaires à la fin de SBP et / ou DPB. J'ai vérifié et ces chiffres ne suivaient pas les valeurs de BP ou ailleurs dans la note. Veuillez me faire savoir si je n'ai pas fourni suffisamment d'informations dans l'enquête ou ici. Votre temps et votre assistance sont grandement appréciés. Merci.
@Shawn Si vos données sont sensiblement différentes de l'échantillon que vous avez fourni, veuillez publier des données supplémentaires / différentes. Avec ce qui est fourni, je crains que ce soit le mieux que je puisse faire. Si vous exécutez cela sur l'exemple fourni, le résultat final est une seule trame de données avec deux vecteurs "SBP", "DBP", comme vous le souhaitez.
Nous pouvons utiliser regmatches / regexpr
de base R
pour extraire les valeurs requises, puis avec read.table
, créer une colonne à deux data.frame
library(dplyr) library(tidyr) tibble(bb) %>% extract(bb, into = c("X1", "X2"), ".*\\b(\\d+)/(\\d+).*", convert = TRUE) # A tibble: 4 x 2 # X1 X2 # <int> <int> #1 114 46 #2 135 67 #3 109 50 #4 188 98
Ou en utilisant strcapture
de base R
data[c("V1", "V2")] <- read.table(text = ...)
Pour créer ceci en tant que nouvelle colonne dans le data.frame d'origine, utilisez soit cbind
pour lier la sortie avec l'ensemble de données d'origine
cbind(data, read.table(text = ...))
soit
strcapture( "(\\d+)\\/(\\d+)", bb, data.frame(X1 = integer(), X2 = integer())) # X1 X2 #1 114 46 #2 135 67 #3 109 50 #4 188 98
Ou en utilisant extraire
de tidyr
read.table(text = regmatches(bb, regexpr('\\d+/\\d+', bb)), sep="/", header = FALSE, stringsAsFactors = FALSE) # V1 V2 #1 114 46 #2 135 67 #3 109 50 #4 188 98
Si nous ne voulons pas supprimer la colonne d'origine, utilisez remove = FALSE
dans extract