1

我有以下数据:

set.seed(123)
M1 <- c(sample(c("AA", "AB", "BB"), 5, replace = T))
M2k <- c(sample (c("AG", "GG", "AA"), 5, replace = T))
M3l <- c(sample (c("AT", "TT", "AA"), 5, replace = T))
M4  <- c(sample (c("CT", "TT", "CC"), 5, replace = T))

  #in real data M1 .......M1000 

myd <- data.frame (M1, M2k, M3l, M4)

我想将每个 M 分成两个 M1a,M1b 用于 M1,M2ka,M2kb 用于 M2k 等等。同样,单元格的内容将被拆分 AB 将是 M1a 列中的 A 和另一个 M1b 列。我还想重新编码 A = 1、B = 2、C = 3、G = 4、T = 5,否则 = NA。

4

4 回答 4

4

编辑 reshape::colsplit将拆分为''

使用reshape::colsplit.

library(reshape)

split_col <- function(.col, data){
 .x <- colsplit( data[[.col]], names =  paste0(.col, letters[1:2])) 

}

# split each column and combine
new_data <- do.call(cbind,lapply(names(myd), split_col, data = myd))
# convert each new column to a factor  with levels 1:5 as requested.
new_data_2 <- do.call(data.frame, 
  lapply(new_data, factor, levels = c('A','B','C','G','T'), labels= 1:5))

  M1a M1b M2ka M2kb M3la M3lb M4a M4b
1   1   1    1    4    1    1   3   3
2   2   2    4    4    5    5   3   5
3   1   2    1    1    1    1   3   5
4   2   2    4    4    5    5   3   5
5   2   2    4    4    1    5   3   3
于 2012-07-03T05:01:41.427 回答
0

mnel 已经给出了一个非常直接的答案。这是我在 GitHub 上玩我的正在处理的包(qdap),虽然还没有在 CRAN 上:

安装 qdap

# install.packages("devtools")
library(devtools)
install_github("qdap", "trinker")

解决问题:

lapply(seq_along(myd),  function(i){
    myd <<- colsplit2df(myd, (i+i-1), paste0(names(myd)[i+i-1], 
        letters[1:2]), sep="")
})

data.frame(apply(myd, 2, function(x) as.numeric(text2color(x, 
    c("A", "B", "C", "G", "T"), c(1:5, NA)))))

这段代码的主要工作是colsplit2df(返回一个 data.frame)和text2col(旨在为 wordcloud 着色重新编码文本;实际上是一个字典查找工具)。这真的不是这些功能的设计目的,只是在玩,看看如何扩展它们。

于 2012-07-03T13:21:51.973 回答
0

这是另一种可能的解决方案,除了我发现它很容易遵循之外没有特别的优势:

myd$M5 = c("AB", "GT", "GA", "QW", "CK") # Add another test column.

mat = as.matrix(myd) # Convert to matrix for speed and indexing benefits.

# Construct new column names.
new_names = character(length=ncol(mat) * 2)
new_names[seq(1, ncol(mat) * 2, 2)] = paste(colnames(mat), "a", sep="")
new_names[seq(2, ncol(mat) * 2, 2)] = paste(colnames(mat), "b", sep="")

# Create empty matrix with correct column names.
newmat = matrix(ncol=ncol(mat) * 2, nrow=nrow(mat))
colnames(newmat) = new_names

# Split columns.
for (i in seq(1, ncol(mat))) {
    newmat[, (i * 2) - 1] = substr(mat[, i], 1, 1)
    newmat[,  i * 2     ] = substr(mat[, i], 2, 2)
}

# Use named vector to recode data.
recode = c(A=1, B=2, C=3, G=4, T=5)
newmat[] = recode[newmat]

newmat
#      M1a M1b M2ka M2kb M3la M3lb M4a M4b M5a M5b
# [1,] "1" "1" "1"  "4"  "1"  "1"  "3" "3" "1" "2"
# [2,] "2" "2" "4"  "4"  "5"  "5"  "3" "5" "4" "5"
# [3,] "1" "2" "1"  "1"  "1"  "1"  "3" "5" "4" "1"
# [4,] "2" "2" "4"  "4"  "5"  "5"  "3" "5" NA  NA 
# [5,] "2" "2" "4"  "4"  "1"  "5"  "3" "3" "3" NA 
于 2012-07-03T07:37:41.730 回答
0

使用具有更稳定解决方案的 qdap:

x <- colsplit2df(myd, 1:ncol(myd), sep="")
colnames(x) <- paste(rep(colnames(myd), each = 2), letters[1:2], sep=".")

##   M1a M1b M2ka M2kb M3la M3lb M4a M4b
## 1   1   1    1    4    1    1   3   3
## 2   2   2    4    4    5    5   3   5
## 3   1   2    1    1    1    1   3   5
## 4   2   2    4    4    5    5   3   5
## 5   2   2    4    4    1    5   3   3
于 2014-02-26T23:55:23.207 回答