Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Convert Rows into Columns by matching string in R

I have number of rows in a list like '

[1,]  "Home"
[2,]  "A"
[3,]  "B"
[4,]  "C"
[5,]  "Home"
[6,]  "D"
[7,]  "E"
[8,]  "Home"
[9,]  "F"
[10,] "G"
[11,] "H"
[12,] "I"

these rows are coming dynamically...after "Home" there can be two,three,four,five or more subcategories....so binding is not working... I have more than 5000 rows and "Home" is common in the start for every subcategories..

I Want it to look like this.

       [,1]   [,2] [,3] [,4] [,5]

[1,]  "Home"  "A"  "B"  "C"   
[2,]  "Home"  "D"  "E"
[3,]  "Home"  "F"  "G"  "H"  "I"

OR

I have also used transpose to covert all rows into columns and on using transpose I got.

   [,1]    [,2] [,3] [,4]  [,5]   [,6]  [,7]  [,8]   [,9] [,10] [,11] [,12]

   "Home"  "A"  "B"  "C"  "Home"   "D"   "E"  "Home"  "F"  "G"   "H"   "I"

any solution would work for me either converting rows in to columns using string match of "Home"
or covert columns into rows using "Home" string match(transpose one)....

Data

x <- c("Home", "A", "B", "C", "Home", "D", "E", "Home", "F", "G", "H", "I")
x <- matrix(x)

The question has been solved...Thankyou for your response... I did it other way around...by running it in a loop and adding the row after every single node ends

List <- c() 

#loop start
nodes <- html_nodes(file,".class a b c ") %>% html_text()
List[[length(List)+1]] = nodes      
#loop ends

library(stringi)
catdf <- stri_list2matrix(List, byrow = TRUE)
catdf <- as.data.frame(catdf)
like image 959
geekzeus Avatar asked Dec 24 '22 08:12

geekzeus


1 Answers

# create the data
x <- as.matrix(c("Home", "A", "B", "C", "Home", "D", "E", "Home", "F" ,"G" ,"H" ,"I"))

# split the data into a list of vectors, wherever "Home" is found
rowstarts <- x == "Home"
rowlist <- split(x, cumsum(rowstarts))

We can then use plyr's ldply function to bind the list into a single data frame:

> plyr::ldply(rowlist, rbind)[-1]
     1 2 3    4    5
1 Home A B    C <NA>
2 Home D E <NA> <NA>
3 Home F G    H    I

And put all together it makes a short one-liner:

ldply(split(x, cumsum(x == "Home")), rbind)[-1]
like image 112
C. Braun Avatar answered Feb 26 '23 21:02

C. Braun