简体   繁体   中英

Rearranging order for a pair in R

I have a column with 10 random numbers, from that I want to create a new column that have switched places for every pair, see example for how I mean. How would you do that?

column    newcolumn
   1         5
   5         1
   7         6
   6         7
   25        67
   67        25
   -10       2
   2         -10
   -50       36
   36        -50

Taking advantage of the fact that R will replicate smaller vectors when adding them to larger vectors, you can:

a <- data.frame(column=c(1,5,7,6,25,67,-10,2,50,36))
a$newColumn <- a$column[seq(nrow(a)) + c(1, -1)]

Something like this.

a <- data.frame(column=c(1,5,7,6,25,67,-10,2,50,36))
a$newColumn <- 0
a[seq(1,nrow(a),by=2),"newColumn"]<-a[seq(2,nrow(a),by=2),"column"]
a[seq(2,nrow(a),by=2),"newColumn"]<-a[seq(1,nrow(a),by=2),"column"]

# results
   column newColumn
1       1         5
2       5         1
3       7         6
4       6         7
5      25        67
6      67        25
7     -10         2
8       2       -10
9      50        36
10     36        50

Here is a base R one-liner: We can cast column as 2 x nrow(df)/2 matrix, swap rows, and recast as vector.

df$newcolumn <- c(matrix(df$column, ncol = nrow(df) / 2)[c(2,1), ]);
#   column newcolumn
#1       1         5
#2       5         1
#3       7         6
#4       6         7
#5      25        67
#6      67        25
#7     -10         2
#8       2       -10
#9     -50        36
#10     36       -50

Sample data

df <- read.table(text =
    "column
   1  
   5  
   7  
   6  
   25
   67
   -10
   2
   -50
   36", header = T)

Another option would be to use ave and rev

transform(df, newCol = ave(x = df$column, rep(1:5, each = 2), FUN = rev))
#   column newCol
#1       1      5
#2       5      1
#3       7      6
#4       6      7
#5      25     67
#6      67     25
#7     -10      2
#8       2    -10
#9     -50     36
#10     36    -50

The part rep(1:5, each = 2) creates a grouping variable ("pairs") for each of which we rev erse the elements.

Here's a compact way:

a$new_col <- c(matrix(a$column,2)[2:1,])

#    column new_col
# 1       1       5
# 2       5       1
# 3       7       6
# 4       6       7
# 5      25      67
# 6      67      25
# 7     -10       2
# 8       2     -10
# 9      50      36
# 10     36      50

The idea is to write in a 2 row matrix, switch the rows, and unfold back in a vector.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM