【问题标题】:Repeated subsetting and arithmetic of dataset based on second dataframe基于第二个数据框的数据集重复子集和算法
【发布时间】:2016-07-25 15:57:25
【问题描述】:

我有一个格式为“dfA”(65,000 行)的数据框:

Chr Pos     NCP     NCP_Ratio
1   72      1.06    0.599
1   371     4.26    1.331
1   633     2.10    2.442
1   859     1.62    1.276
1   1032    7.62    4.563
1   1199    6.12    4.896
1   1340    13.22   23.607

我希望在dfA 的每一行中使用ChrPos 的值来顺序子集第二个data.frame dfB 的形式:

Chr Pos Watson  Crick
1   1   5       0
1   2   5       0
1   4   1       0
1   6   1       0
1   7   1       0
1   8   2       0
1   9   2       0
1   12  1       0
1   14  1       0
1   15  2       0
1   22  1       0

dfB 有大约 400 万行。

每次我对dfB 进行子集化时,我都想根据Pos 中的范围检索感兴趣区域的值(即dfAPos 的值的+/- 1000),并将它们添加到最初预填充零的第三个 data.frame dfC

我通过循环遍历dfA 的每一行来完成这项工作。但由于有 65,000 行,因此需要数小时。所以我的问题是:

  1. 有没有更好/更有效的方法?

  2. 我的代码的哪一部分让这个速度变慢了这么多?”

我的代码:

temp=NULL
width=300 # Region upstream and downstream of centrepoint #
padding=50 # Add some padding area to table #
width1=width+padding
dfC=data.frame(NULL)
dfC[1:((width1*2)+1),"Pos"]=(1:((width1*2)+1)) # Create Pos column #

# Prefill dfC table with zeros #
dfC[1:((width1*2)+1),"Watson"]=0
dfC[1:((width1*2)+1),"Crick"]=0

for (chrom in 1:16) { # LOOP1. Specify which chromosomes to process #

  dfB.1=subset(dfB,Chr==chrom) # Make temp copy of the dataframes for each chromosome #
  dfA.1=subset(dfA, Chr==chrom)

for (i in 1:nrow(dfA.1)) { # LOOP2: For each row in dfA:

  temp=subset(dfB.1, Pos>=(dfA.1[i,"Pos"]-width1) & Pos<=(dfA.1[i,"Pos"]+width1)) # Create temp matrix with hits in this region
  temp$Pos=temp$Pos-dfA.1[i,"Pos"]+width1+1
  dfC[temp$Pos,"Watson"]=dfC[temp$Pos,"Watson"]+temp[,"Watson"]
  dfC[temp$Pos,"Crick"]=dfC[temp$Pos,"Crick"]+temp[,"Crick"]

} # End of LOOP2 #
} # End of LOOP1 #

示例输出采用以下形式 - 其中 Pos 包含 1 到 2000 的值(表示 dfA 中每个中心 Pos 位置两侧的 -1000 到 +1000 区域),Watson/Crick 列包含命中的总和每个位置。

Pos Watson  Crick
1   15      34
2   35      32
3   11      26
4   19      52
5   10      23
6   32      17
7   21      6
8   15      38
9   17      68
10  28      54
11  27      35
etc

【问题讨论】:

  • 如果您包含示例代码的预期输出,将会很有帮助。另外,考虑以dput 的形式发布您的数据
  • 感谢您在编辑/格式化方面的帮助。我添加了示例输出。我不熟悉 dput,但我现在正在阅读帮助。

标签: r


【解决方案1】:

我只是清理了你的代码,所以不要指望有很大的改进,但我 认为这个版本可能会稍微快一点。

width <- 300
padding <- 50
width1 <- width + padding    
dfC <- data.frame(Pos=1:((width1*2)+1), Watson=0, Crick=0)
for (chrom in 1:16) {
    dfB1 <- subset(dfB, Chr == chrom)
    for (pos in dfA$Pos[dfA$Chr == chrom]) {
        dfB2 <- dfB1[(dfB1$Pos >= pos - width1) & (dfB1$Pos <= pos + width1), ]
        rows <- dfB2$Pos - pos + width1 + 1
        dfC$Watson[rows] <- dfC$Watson[rows] + dfB2$Watson
        dfC$Crick[rows] <- dfC$Crick[rows] + dfB2$Crick
    }
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2011-12-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-04-28
    • 2016-03-12
    相关资源
    最近更新 更多