假设我有以下向量:
c(4, 5, 5, 8, 12, 12, 12, 13, 15, 15, 18, 19, 20, 23, 37, 37, 37, 37, 37, 41)
我想根据它们的值“分组”它们的元素:不同的数字< = 3应该被认为属于同一个组。 在这种情况下,我希望,对于向量中出现的每个数字,获取所有接近它的数字。 例如,
4 --> c(4,5,5,8)
5 --> c(4,5,5,8)
8 --> c(5,8)
12 --> c(12,12,12,13,15,15)
等
可能,获取他们的索引也很有用...... 有没有聪明的方法来实现这个目标?
答案 0 :(得分:9)
你可以使用这个小功能:
similar <- function(vec, val, bound = 3, index = F) {
close.index <- which(abs(vec - val) <= bound)
if (index) return(close.index)
return(vec[close.index])
}
x <- c(4, 5, 5, 8, 12, 12, 12, 13, 15, 15, 18, 19, 20, 23, 37, 37, 37, 37, 37, 41)
similar(x, 5)
# [1] 4 5 5 8
similar(x, 5, index = T)
# [1] 1 2 3 4
similar(x, 5, bound = 7)
# [1] 4 5 5 8 12 12 12
答案 1 :(得分:2)
也许不是最优雅的版本,但这会做你想要的吗?
abs
使用for (i in 1:length(vals)) print(which(abs(x-vals[i]) <= 3))
for (i in 1:length(vals)) print(x[which(abs(x-vals[i]) <= 3)])
确实有点优雅。
# import "GoogleMapsM4B/GoogleMaps.h"
答案 2 :(得分:2)
这是一个简短的解决方案,为您提供所有组列表:
x = c(4, 5, 5, 8, 12, 12, 12, 13, 15, 15, 18, 19, 20, 23, 37, 37, 37, 37, 37, 41)
m = unique(x)
setNames(apply(abs(outer(m,m,'-')), 2, function(u) m[u<=3]),m)
#$`4`
#[1] 4 5
#$`5`
#[1] 4 5 8
#$`8`
#[1] 5 8
#$`12`
#[1] 12 13 15
#$`13`
#[1] 12 13 15
#$`15`
#[1] 12 13 15 18
#$`18`
#[1] 15 18 19 20
#$`19`
#[1] 18 19 20
#$`20`
#[1] 18 19 20 23
#$`23`
#[1] 20 23
#$`37`
#[1] 37
#$`41`
#[1] 41
对于索引,可以轻松应用相同的概念:
setNames(apply(abs(outer(m,m,'-')), 2, function(u) which(x %in% m[u<=3])),m)
答案 3 :(得分:0)
使用数字作为“键”创建列表可能会有所帮助:
data <- c(4, 5, 5, 8, 12, 12, 12, 13, 15, 15, 18, 19, 20, 23, 37, 37, 37, 37, 37, 41)
uniques <- unique(data)
myGroups <- lapply(
uniques,
function(n) Filter(
function(x) abs(x - n) <= 3,
data
)
)
names(myGroups) <- uniques
myIndices <- lapply(
uniques,
function(n) which(abs(data - n) <= 3)
)
names(myIndices) <- uniques
然后,要访问“12”的组和索引,请说:
> myGroups[['12']]
[1] 12 12 12 13 15 15
> myIndices[['12']]
[1] 5 6 7 8 9 10