다시 입력하지 않고 data.frame () 내에서 열 이동
완전히 새로운 data.frame ()을 입력하지 않고 data.frame의 한 위치에서 다음 위치로 열을 이동하는 방법이 있습니까?
예를 들면 :
a <- b <- c <- d <- e <- f <- g <- 1:100
df <- data.frame(a,b,c,d,e,f,g)
이제 "a"앞에 "g"를 원한다고 가정 해 보겠습니다.
다시 입력 할 수 있습니다.
df <- data.frame(g,a,b,c,d,e,f)
그러나 더 빠른 방법이 없습니까? (1500 개 이상의 열을 상상해보세요)
한 가지 방법은 다음과 같습니다.
> col_idx <- grep("g", names(df))
> df <- df[, c(col_idx, (1:ncol(df))[-col_idx])]
> names(df)
[1] "g" "a" "b" "c" "d" "e" "f"
이 subset
함수에는 select
이름으로 열 범위를 선택하는 편리한 방법을 제공 하는 멋진 인수가 있습니다.
df <- subset(df, select=c(g,a:f))
최근에이 함수를 작성했습니다 moveme
. 열 순서를 섞을 목적으로 벡터에서 작동하도록 설계되었습니다.
기능은 다음과 같습니다.
moveme <- function (invec, movecommand) {
movecommand <- lapply(strsplit(strsplit(movecommand, ";")[[1]],
",|\\s+"), function(x) x[x != ""])
movelist <- lapply(movecommand, function(x) {
Where <- x[which(x %in% c("before", "after", "first",
"last")):length(x)]
ToMove <- setdiff(x, Where)
list(ToMove, Where)
})
myVec <- invec
for (i in seq_along(movelist)) {
temp <- setdiff(myVec, movelist[[i]][[1]])
A <- movelist[[i]][[2]][1]
if (A %in% c("before", "after")) {
ba <- movelist[[i]][[2]][2]
if (A == "before") {
after <- match(ba, temp) - 1
}
else if (A == "after") {
after <- match(ba, temp)
}
}
else if (A == "first") {
after <- 0
}
else if (A == "last") {
after <- length(myVec)
}
myVec <- append(temp, values = movelist[[i]][[1]], after = after)
}
myVec
}
사용법은 간단합니다. 다음을 시도하십시오.
moveme(names(df), "g first")
moveme(names(df), "g first; a last; e before c")
물론 열을 재정렬하는 데 사용하는 data.frame
것은 간단합니다.
df[moveme(names(df), "g first")]
그리고 data.table
s (참조로 이동, 사본 없음) :
setcolorder(dt, moveme(names(dt), "g first"))
기본 옵션은 다음과 같습니다.
- 먼저
- 마지막
- 전에
- 후
복합 이동은 세미콜론으로 구분됩니다.
사용 select
로부터 dplyr의 패키지와 그 everything()
기능은 data.frame의 시작이나 끝으로 특정 열을 이동합니다.
처음으로 이동 :
library(dplyr)
df %>%
select(g, everything())
끝으로 이동 :
df %>%
select(-a, everything())
또는 %>%
파이프 연산자가 없으면 각각 select(df, g, everything())
및 select(df, -a, everything())
입니다.
여기 내 해결책이 있습니다.
df[c(7,1:6)]
또는 열 이름으로 재정렬 할 수도 있습니다.
df[c("g",names(df)[-7])]
이것은 약간 더 우아하고 맨 왼쪽의 처음 몇 개의 열을 정렬하고 나머지는 오른쪽에 정렬하지 않은 채로 둘 수 있습니다.
ordered_columns_leftside=c('var10','var34','var8')
df=df[c(ordered_columns_leftside, setdiff(names(df),ordered_columns_leftside))]
다음은 열 이름을 기반으로 거대한 데이터 프레임에서 'n'번째 열을 2 번째 위치로 이동하는 데 사용한 유사한 방법입니다.
열을 첫 번째 위치로 이동 :
## Move a column with name "col_name" to first column
colX <- grep("^col_name", colnames(df.original))
# get the column position from name
df.reordered.1 <- df.original[,c(colX,1:(colX-1), (colX+1):length(df.original))]
# get new reordered data.frame
# if the column is the last one, error "undefined columns selected" will show up. Then do the following command instead of this
df.reordered.1 <- df.original[,c(colX,1:(colX-1)]
# get new reordered data.frame, if the column is the last one
어디에서나 'n'번째 위치까지
## Move a column with name "col_name" to column position "n",
## where n > 1 (in a data.frame "df.original")
colX <- grep("^col_name", colnames(df.original))
# get the column position from name
n <- 2
# give the new expected column position (change to the position you need)
df.reordered.2 <- df.original[,c(1:(n-1), colX, n:(colX-1), (colX+1):length(df.original))]
# get new reordered data.frame
## Optional; to replace the original data frame with sorted data.frame
## if the sorting looks good
df.original <- df.reordered.2
rm(df.reordered.2) # remove df
이것은 매우 오래된 게시물이지만 데이터 프레임 내에서 열 위치를 동적으로 변경하는이 코드를 개발했습니다. n 값과 열 이름 (여기서 "g")을 변경하고 새 열 배열로 데이터 프레임을 가져옵니다.
df1 = subset(df, select = c(head(names(df),n=3),"g", names(df) [! names(df) %in% c(head(names(df),n=3),"g")]))
예에서와 같이 순서 변경이 시프트 인 shift
경우 taRifx
패키지 의 함수를 사용할 수 있습니다 . 벡터에 작용하므로 열 이름에 적용합니다.
> a <- b <- c <- d <- e <- f <- g <- 1:5
> df <- data.frame(a,b,c,d,e,f,g)
> df[, taRifx::shift(seq_along(df),-1)]
g a b c d e f
1 1 1 1 1 1 1 1
2 2 2 2 2 2 2 2
3 3 3 3 3 3 3 3
4 4 4 4 4 4 4 4
5 5 5 5 5 5 5 5
사실이 shift
함수는 데이터 프레임에도 적용 할 수 있지만 예상과는 다릅니다. 함수를 작성할 수 있습니다.
> shift_df <- function(df, n) df[, taRifx::shift(seq_along(df),n)]
> shift_df(df, -1)
g a b c d e f
1 1 1 1 1 1 1 1
2 2 2 2 2 2 2 2
3 3 3 3 3 3 3 3
4 4 4 4 4 4 4 4
5 5 5 5 5 5 5 5
> shift_df(df, 2)
c d e f g a b
1 1 1 1 1 1 1 1
2 2 2 2 2 2 2 2
3 3 3 3 3 3 3 3
4 4 4 4 4 4 4 4
5 5 5 5 5 5 5 5
다음은 데이터 프레임에서 열을 이동하기 위해 작성한 간단하지만 유연한 함수입니다.
move.col <- function(df, move_this, next_to_this, before = FALSE) {
if (before==FALSE)
df[,c(match(setdiff(names(df)[1:which(names(df)==next_to_this)],move_this),names(df)),
match(move_this,names(df)),
match(setdiff(names(df)[which(names(df)==next_to_this):ncol(df)],c(next_to_this,move_this)),names(df)))]
else
df[,c(match(setdiff(names(df)[1:(which(names(df)==next_to_this))],c(next_to_this,move_this)),names(df)),
match(move_this,names(df)),
match(setdiff(names(df)[(which(names(df)==next_to_this)):ncol(df)],move_this),names(df)))]
}
Usage: Specify the data frame (df
), the column name you want to move (move_this
), and the column name of which you want to move beside (next_to_this
). By default, the function will move the move_this
column after the next_to_this
column. You can specify before = TRUE
to move move_this
before next_to_this
.
Examples:
- Move "b" after "g" (i.e., make "b" last column).
move.col(df, "b", "g")
- Move "c" after "e".
move.col(df, "c", "e")
- Move "g" before "a" (i.e., make "g" first column).
move.col(df, "g", "a", before=TRUE)
- Move "d" and "f" before "b" (i.e., move multiple columns).
move.col(df,c("d","f"),"b", before=TRUE)
Most solutions seem overly verbose or lack encapsulation. Here's another way to solve the problem
push_left <- function(df, pushColNames){
df[, c(pushColNames, setdiff(names(df), pushColNames))]
}
push_left(iris, c("Species", "Sepal.Length"))
I found a pretty simple way of doing this that suited my needs and doesn't take much time.
You have the following column names: "a", "b", "c", "d", "e", "f", "g", "h", "i", "j"
Move "d" to second position (after "a"):
attach(df)
df <- cbind(a, d, df[,c(2:3,5:10)])
Move "j" to 4th position (after "c"):
df <- cbind(df[,c(1:3)], j, df[,c(4:9)])
I would like to contribute another universal working approach, similar to the previous answers of rcs, Manuel and Scott Kaiser, which only work in specific cases:
move<-function(new.pos,nameofcolumn,dfname) {
col_idx <- grep(nameofcolumn, names(dfname))
if (length(col_idx)==0){print("invalid column name");return(dfname)} else {
if(new.pos>ncol(dfname)){print("invalid column number");return(dfname)} else {
if (new.pos==1) {
b<-dfname[ , c( col_idx, c((new.pos):ncol(dfname))[-(abs(new.pos-1-col_idx))] )]
}
else if(col_idx==1 & new.pos==ncol(dfname)){
b<-dfname[ , c((1:(new.pos-1)+1), col_idx )]
}
else if(col_idx==1){
b<-dfname[ , c((1:(new.pos-1)+1), col_idx, c((new.pos+1):ncol(dfname)) )]
}
else if(new.pos==ncol(dfname)){
b<-dfname[ , c((1:(new.pos))[-col_idx], col_idx)]
}
else if(new.pos>col_idx){
b<-dfname[ , c((1:(new.pos))[-col_idx], col_idx, c((new.pos+1):ncol(dfname)) )]
}
else{
b<-dfname[ , c((1:(new.pos-1)), col_idx, c((new.pos):ncol(dfname))[-(abs(new.pos-1-col_idx))] )]
}
return(b)
if(length(ncol(b))!=length(ncol(dfname))){print("error")}
}
}}
Usage:
a <- b <- c <- d <- e <- f <- g <- 1:5
df <- data.frame(a,b,c,d,e,f,g)
move(1,"g",df)
Here is one function that might help
- df: the dataframe
- ColName: the name of the column(s) to be moved
- Position: the column number that you want the moved column to appear
moveCol <- function(df,ColName,Position=1) {
D <- dim(df)[2]
DFnames <- names(df)
if (Position>D+1 | Position<1) {
warning(paste0('Column position ',sprintf('%d',Position), ' is out of range [1-',sprintf('%d',D),']'))
return()
}
for (i in ColName) {
x <- i==DFnames
if (all(!x)) {
warning(paste0('Column \"', i, '\" not found'))
} else {
D1 <- seq(D)
D1[x] = Position - 0.5
df<- df[order(D1)]
}
}
return(df)
}
@David asked how to move "G" to an arbitrary position, such as 4. Building on @rcs answer,
new.pos <- 4
col_idx <- grep("g", names(df))
df <- df[ , c((1:new.pos)[-col_idx], col_idx, c((new.pos):ncol(df))[-col_idx])]
ReferenceURL : https://stackoverflow.com/questions/3369959/moving-columns-within-a-data-frame-without-retyping
'programing tip' 카테고리의 다른 글
Python UnicodeDecodeError-인코딩을 오해하고 있습니까? (0) | 2021.01.09 |
---|---|
헤더가 그대로있는 Python을 사용하여 CSV 파일을 가져 오는 방법 (첫 번째 열이 숫자가 아닌 열임) (0) | 2021.01.09 |
CSS를 사용하여 모서리 자르기 (0) | 2021.01.09 |
웹팩을 사용하는 여러 HTML 파일 (0) | 2021.01.08 |
Visual Studio에서 특정 줄 번호로 파일 열기 (0) | 2021.01.08 |