Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

R match and replace pattern in data frame

Tags:

dataframe

r

I have a data frame that contains three types AA, AB and BB. After that, there are samples 1000 to 1005 which contains different types. However, some of the strings are type BA not like the type 2 AB, therefore I want to change the strings to match the type 2 category.

Input:

Type 1  Type 2  Type 3  1000    1001    1002    1003    1004    1005
AA      AB      BB      BB      BB      AB      BA      AA      BA
CC      AC      AA      CA      CA      CC      AA      AA      AC
EE      EF      FF      EF      FF      FE      FE      EE      FF

Desired output:

Type 1  Type 2  Type 3  1000    1001    1002    1003    1004    1005
AA      AB      BB      BB      BB      AB      AB      AA      AB
CC      AC      AA      AC      AC      CC      AA      AA      AC
EE      EF      FF      EF      FF      EF      EF      EE      FF
like image 581
Peter Chung Avatar asked Sep 09 '26 15:09

Peter Chung


1 Answers

If we need to change the numeric column values based on the values in 'Type_2' column i.e. reverse values should be changed to that of 'Type_2', then one option is apply with MARGIN = 1 (to loop over the rows), subset the elements from 4 to the last one (x[4:length(x)] - that corresponds to the elements in the numeric column names), check if the first character is not equal to second character (substr(x1, 1, 1) != substr(x1, 2, 2)) and (&) whether it is not equal to the 'Type_2' (x1 != x[2]), then we use sub to reverse the order of elements in 'x1' or else return 'x1' (ifelse(...)), assign the output back to the original vector (x[4:length(x)]), return the 'x', transpose (t) the output and assign the values back to 'df1'.

df1[] <- t(apply(df1, 1, FUN = function(x) {
               x1 <- x[4:length(x)]
               x[4:length(x)] <- ifelse(substr(x1,1,1)!= substr(x1,2,2) & x1 != x[2],
                                     sub("(.)(.)", "\\2\\1", x1), x1)
                 x}))
 df1
 #  Type_1 Type_2 Type_3 1000 1001 1002 1003 1004 1005
 #1     AA     AB     BB   BB   BB   AB   AB   AA   AB
 #2     CC     AC     AA   AC   AC   CC   AA   AA   AC
 #3     EE     EF     FF   EF   FF   EF   EF   EE   FF

data

 df1 <-  structure(list(Type_1 = c("AA", "CC", "EE"), Type_2 = c("AB", 
 "AC", "EF"), Type_3 = c("BB", "AA", "FF"), `1000` = c("BB", "CA", 
 "EF"), `1001` = c("BB", "CA", "FF"), `1002` = c("AB", "CC", "FE"
 ), `1003` = c("BA", "AA", "FE"), `1004` = c("AA", "AA", "EE"), 
`1005` = c("BA", "AC", "FF")), .Names = c("Type_1", "Type_2", 
 "Type_3", "1000", "1001", "1002", "1003", "1004", "1005"), 
  class =  "data.frame", row.names = c(NA, -3L))
like image 108
akrun Avatar answered Sep 12 '26 08:09

akrun