我有一个大约1000个元素的向量,从大约1到10,我希望所有元素的乘积乘以模10 ^ 6。即,我想要类似于
的东西x <- as.integer(runif(1000, 1, 10))
prod(x) %% 1000000
但是,由于prod(x)
评估为Inf
,因此上述内容只会返回NaN
。
在我的实际应用中(这并不是最小的,所以我不会把它放在这里),我已经用for
循环完成了这个,比如
x <- as.integer(runif(1000, 1, 10))
for (i in 1:length(x)) {
if (i == 1) {
y <- x[i]
} else {
y <- y * x[i]
y <- y %% 1000000
}
}
y
最初我只是想寻求一个比for
循环更好的解决方案的帮助,假设我应该在R中避免这个。但是,在写这个问题时,我现在同样感到困惑的是事实上,我似乎无法为for
循环生成有效的MWE。上面的代码返回0
,但是当我删除as.integer()
时它可以正常工作。我花了比我更长的时间来承认试图弄清楚为什么会这样,但是我很难过。
然后有两个问题:
as.integer
呢?)gmp
包的东西。我已尝试使用sapply
/ lapply
,但到目前为止无济于事。我发现了其他语言提出的类似问题,但我很难解读这些术语中的答案,我很害怕。
答案 0 :(得分:0)
让我们看看会发生什么:
set.seed(42)
x <- as.integer(runif(1000, 1, 10))
y <- integer(1000)
for (i in 1:length(x)) {
if (i == 1) {
y[i] <- x[i]
} else {
y[i] <- y[i-1] * x[i]
y[i] <- y[i] %% 1000000
}
}
y[1:30]
# [1] 9 81 243 1944 11664 58320 408240 816480 898880 292160 460800 225600 30400 91200 456000 104000 936000
#[18] 872000 360000 160000 440000 880000 920000 280000 280000 400000 600000 400000 0 0
好的,所以问题出现在第29次迭代中:
400000 * x[29]
#[1] 2e+06
为什么浮点数不会发生?
set.seed(42)
x <- (runif(1000, 1, 10))
y <- integer(1000)
for (i in 1:length(x)) {
if (i == 1) {
y[i] <- x[i]
} else {
y[i] <- y[i-1] * x[i]
y[i] <- y[i] %% 1000000
}
}
y[1:30]
#[1] 9.233254e+00 8.710356e+01 3.114175e+02 2.638961e+03 1.788083e+04 1.014176e+05 7.737451e+05 7.115236e+05 9.187133e+05
#[10] 7.484847e+05 8.319994e+05 2.167078e+05 3.966498e+04 1.308492e+05 6.752649e+05 3.880944e+05 8.048925e+05 6.559748e+05
#[19] 4.602498e+05 7.812873e+05 1.380611e+05 3.104154e+05 7.312040e+04 6.961072e+05 2.125757e+05 1.963559e+05 8.859247e+05
#[28] 1.076669e+05 5.407815e+05 6.096419e+05
如你所见,你永远不会得到1e6的倍数。
请注意,由于您在每次迭代中计算模数,因此您的循环与向量化尝试不同。
您可以考虑使用任意精度数作为替代(参见包Rmpfr)。或者使用更智能的算法。