Reputation:
I have a data frame, where every row has a value, and every block of 100 rows has an index (between 1 and 10). I would like to sort the index blocks in a particular order, but am unsure how to do that:
N=1000
value = runif(N, min=0, max=100)
index = rep(1:10, each=100)
DF=data.frame(value,index)
ord = c(1,4,6,3,7,9,8,2,5,10)
So basically, I would like the index column of DF to be ordered in blocks of the order specified in ord, instead of the index column of DF being ordered as 1,2,3,4,5,6,7,8,9,10.
Any advice would be appreciated!
Upvotes: 3
Views: 1968
Reputation: 92282
You could simply convert index
to factor and set the levels as in ord
order and then sort the data as in
DF$index <- factor(DF$index, levels = ord)
DF[order(DF$index), ]
If you don't want to "alter your original data" you could simply create a separate index as in
indx <- factor(DF$index, levels = ord)
DF[order(indx), ]
Additional otion is to order your data set by reference using setorder
from the data.table
package
library(data.table)
setorder(setDT(DF)[, index := factor(index, levels = ord)], index)
Upvotes: 4
Reputation: 23
Here is my proposal:
#Genreate the data
N<-1000
value <- runif(N, min=0, max=100)
index <- rep(1:10, each=100)
DF<-data.frame(value,index)
ord <- c(1,4,6,3,7,9,8,2,5,10)
#Create a list with the data sorted by the provided order
newDF<-apply(matrix(ord,,ncol=1),1,function(x) DF[DF[,2]==x,])
#Unlist the list into a dataframe
do.call(rbind.data.frame,newDF)
Upvotes: 2
Reputation: 93813
Without altering your original data, you can use merge
with sort=FALSE
:
merge(data.frame(index=ord), DF, by="index", sort=FALSE)
# ord value
#1 1 37.29915
#2 1 30.09436
#3 4 18.05961
#4 4 46.73024
#5 6 93.15545
#6 6 69.33484
#7 3 70.92353
#8 3 81.63010
#9 7 22.23649
#10 7 32.36390
# etc etc
Upvotes: 1