gpt4 book ai didi

r - 向量化插入元素

转载 作者:行者123 更新时间:2023-12-04 12:01:07 24 4
gpt4 key购买 nike

我写了一个 R 函数 insert 来在 a 的给定位置 p 插入一个给定的元素 e矢量v

这里是:

insert <- function(v, e, p) {
if (length(e) != 1 || length(p) != 1) {
stop('supported the insertion of only one element per call.')
}
len <- length(v)
nms <- names(v)
enm <- names(e)
res <- NULL
if (p > 1 && p <= len) {
res <- c(v[1:(p-1)], e, v[p:len]) # insert
} else if (p == 1) {
res <- c(e, v) # prepend
} else if (p == (len+1)) {
res <- c(v, e) # append
} else {
stop('wrong position')
}
if (!is.null(enm)) {
names(res) <- insert(nms, enm, p)
}
res
}

请注意,与 R 中的几乎所有内容一样,此函数返回一个新向量。此外(参见递归调用),它还插入元素的名称,如果有的话。

这是一个简单的使用示例:

a <- c(1,2,3,4,5,7,8,10)
names(a) <- c(letters[1:5], letters[7:8], letters[10])
a
# a b c d e g h j
# 1 2 3 4 5 7 8 10
b <- c(9)
names(b) <- letters[9]
insert(a, b, 8)
# a b c d e g h i j
# 1 2 3 4 5 7 8 9 10

我正在尝试编写此函数的矢量化(高效)版本

现在,我写了一个优雅的解决方案:

vinsert <- function(v, elems, positions) {
out <- v
for (i in 1:length(elems)) {
out <- insert(out, elems[i], positions[i])
}
out
}

这里是一个简单的使用示例:

a <- c(1,2,3,4,5,7,8,10)
names(a) <- c(letters[1:5], letters[7:8], letters[10])
a
# a b c d e g h j
# 1 2 3 4 5 7 8 10
z <- c(6,9)
names(z) <- c(letters[6], letters[9])
z
# f i
# 6 9
vinsert(a, z, z)
# a b c d e f g h i j
# 1 2 3 4 5 6 7 8 9 10

因此,关于这两个函数(insertvinsert)我正在考虑的问题是:

  1. 返回一个新的向量或修改向量并返回它?
  2. Rcpp 写一个等价的函数?
  3. 是否可以使用一阶 R 函数编写等效函数?

任何建议、帮助或更优雅、更有效的解决方案?提前致谢。

最佳答案

似乎存在许多问题,例如,插入顺序如何受先前插入的影响,以及插入多个元素的序列时该怎么做。这里我们有一个原始序列

x <- letters[1:10]

还有一些我们想插入的东西

v <- LETTERS[1:4]

以及我们想插入它们的地方

at <- c(4, 7, 2, 6)

插入的一种方法是找出新索引值 at 相对于原始索引值的顺序; order 提供稳定订单

o <- order(c(seq_along(x), at))

然后进行插入

> c(x, v)[o]
[1] "a" "b" "C" "c" "d" "A" "e" "f" "D" "g" "B" "h" "i" "j"

插入规则和你原来的不太一样

> o = order(c(seq_along(a), z))
> c(a, z)[o]
a b c d e g f h j i
1 2 3 4 5 7 6 8 10 9

关于r - 向量化插入元素,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15937681/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com