【发布时间】:2012-03-20 13:35:32
【问题描述】:
我正在使用 R 中的一个大整数向量(大约 1000 万个整数),我需要从这个向量中找到相差 500 或更少的每一对不同的整数,并制作它们差异的直方图(即每对,第二个减去第一个)。
这是完全非矢量化的代码,用于非常缓慢地完成我想做的事情:
# Generate some random example data
V <- round(rnorm(100) * 1000)
# Prepare the histogram
my.hist <- rep(0, 500)
names(my.hist) <- as.character(seq(1,500))
for (x1 in V) {
for (x2 in V) {
difference = x2 - x1
if (difference > 0 && difference <= 500) {
my.hist[difference] = my.hist[difference] + 1
}
}
}
(假设每个整数都是唯一的,所以difference > 0 位是可以的。这是允许的,因为我实际上并不关心差异为零的任何情况。)
下面是一些矢量化内循环的代码:
my.hist2 <- rep(0, 500)
names(my.hist2) <- as.character(seq(1,500))
for (x1 in V) {
differences <- V[V > x1 & V <= x1+500] - x1
difftable <- table(differences)
my.hist2[names(difftable)] = my.hist2[names(difftable)] + difftable
}
这肯定比第一个版本快。然而,当V 仅包含 500000 个元素(半百万)时,即使这个变体也已经太慢了。
我可以在没有任何显式循环的情况下执行此操作,如下所示:
X <- combn(V, 2)
# X is a matrix with two rows where each column represents a pair
diffs <- abs(X[2,] - X[1,])
my.hist3 <- table(diffs[diffs <= 500])
但是矩阵 X 将包含 10e6 * (10e6 - 1) / 2,或大约 50,000,000,000,000 列,这可能是个问题。
那么有没有办法在不显式循环(太慢)或扩展所有对的矩阵(太大)的情况下做到这一点?
如果你想知道为什么我需要这样做,我正在实现这个:http://biowhat.ucsd.edu/homer/chipseq/qc.html#Sequencing_Fragment_Length_Estimation
【问题讨论】:
-
我是否正确理解您有 50,000,000,000,000 列,每列包含 10,000,000 个元素?我很想看到这个问题得到解决 :) 规模使它成为一个了不起的问题。
-
@user306848:我认为 Ryan 的意思是
combn将返回一个 2 x 50E12 矩阵对(所有可能的组合)。 -
是的,@jbaums 是正确的。
-
感谢您的澄清 :)
-
你的向量的范围/分布是什么样的?有多少个唯一整数?
标签: performance r iteration nested-loops