在向量中找到 n 个最接近位置 t 的非 NA 值
Find n closest non-NA values to position t in vector
对于那些有 R 经验的人来说,这可能是一个简单的问题,但这是我(新手)正在努力解决的问题...
我有两个向量示例,它们对于我要解决的问题是常见的,A
和 B
:
A <- c(1,3,NA,3,NA,4,NA,1,7,NA,2,NA,9,9,10)
B <- c(1,3,NA,NA,NA,NA,NA,NA,NA,NA,2,NA,9)
#and three scalars
R <- 4
t <- 5
N <- 3
还有第四个标量,n
,其中 0<=n<=N
。一般来说,N <= R
.
我想找到 n
最接近 t
的非 NA
值,使它们落在以 t
为中心的半径 R
内。即,搜索半径 R
包含 R+1
个值。例如A,搜索半径序列为(3,NA,3,NA,4,NA,1)
,其中t=NA
,搜索半径序列中的中间值
预期答案可以是 A 的两个结果之一:
answerA1 <- c(3,4,1)
或
answerA2 <- c(3,4,3)
B 的预期答案:
answerB <- c(1,3)
我如何才能以最省时 space 的方式完成这项任务?欢迎使用衬垫、环等。如果非要选一个,那是速度!
提前致谢!
注:
对于这种情况,我了解到第三个最接近的非 NA
值可能涉及为第三个值选择落在 t
右侧或左侧的首选项(如所示以上两个可能的答案)。我对这个值是落在 t
的左边还是右边没有偏好,但是,如果有办法让它随机发生,(第三个值是落在右边还是左边)那将是理想的(但是,同样,这不是必需的)。
是这样的吗?
thingfinder <- function(A,R,t,n) {
left <- A[t:(t-R-1)]
right <- A[t:(t+R+1)]
leftrightmat <- cbind(left,right)
raw_ans <- as.vector(t(leftrightmat))
ans <- raw_ans[!is.na(raw_ans)]
return(ans[1:n])
}
thingfinder(A=c(1,3,NA,3,NA,4,NA,1,7,NA,2,NA,9,9,10), R=3, t=5, n=3)
## [1] 3 4 3
这当然会优先考虑左侧。
一个相对简短的解决方案是:
orderedA <- A[order(abs(seq_len(length(A)) - t))][seq_len(R*2)]
n_obj <- min(sum(is.na(orderedA)), N, length(na.omit(orderedA)))
res <- na.omit(orderedA)[seq_len(n_obj)]
res
#[1] 3 4 3
进一步分解步骤如下:
顺序A,通过与感兴趣位置的绝对距离,t
。
- 代码为:
A[order(abs(seq_len(length(A)) - t))]
子集到第一个 R*2
元素(因此这将得到 R
内 t
两侧的元素。
- 代码为:
[seq_len(R*2)]
- 获取第
min(N, # of non-NA, len of non-NA)
个元素
- 代码为:
min(sum(is.na(orderedA)), N, length(na.omit(orderedA)))
- 放弃
NA
- 代码为:
na.omit()
- 取第3步中确定的第一个元素(以较小者为准)
- 代码为:
[seq_len(n_obj)]
如果对其他人有帮助,@Mike H. 还为我提供了 return 与所需向量元素相关联的索引 positions
的解决方案 res
:
A <- setNames(A, seq_len(length(A)))
orderedA <- A[order(abs(seq_len(length(A)) - t))][seq_len(R*2)]
n_obj <- min(sum(is.na(orderedA)), N, length(na.omit(orderedA)))
res <- na.omit(orderedA)[seq_len(n_obj)]
positions <- as.numeric(names(res))
对于那些有 R 经验的人来说,这可能是一个简单的问题,但这是我(新手)正在努力解决的问题...
我有两个向量示例,它们对于我要解决的问题是常见的,A
和 B
:
A <- c(1,3,NA,3,NA,4,NA,1,7,NA,2,NA,9,9,10)
B <- c(1,3,NA,NA,NA,NA,NA,NA,NA,NA,2,NA,9)
#and three scalars
R <- 4
t <- 5
N <- 3
还有第四个标量,n
,其中 0<=n<=N
。一般来说,N <= R
.
我想找到 n
最接近 t
的非 NA
值,使它们落在以 t
为中心的半径 R
内。即,搜索半径 R
包含 R+1
个值。例如A,搜索半径序列为(3,NA,3,NA,4,NA,1)
,其中t=NA
,搜索半径序列中的中间值
预期答案可以是 A 的两个结果之一:
answerA1 <- c(3,4,1)
或
answerA2 <- c(3,4,3)
B 的预期答案:
answerB <- c(1,3)
我如何才能以最省时 space 的方式完成这项任务?欢迎使用衬垫、环等。如果非要选一个,那是速度!
提前致谢!
注:
对于这种情况,我了解到第三个最接近的非 NA
值可能涉及为第三个值选择落在 t
右侧或左侧的首选项(如所示以上两个可能的答案)。我对这个值是落在 t
的左边还是右边没有偏好,但是,如果有办法让它随机发生,(第三个值是落在右边还是左边)那将是理想的(但是,同样,这不是必需的)。
是这样的吗?
thingfinder <- function(A,R,t,n) {
left <- A[t:(t-R-1)]
right <- A[t:(t+R+1)]
leftrightmat <- cbind(left,right)
raw_ans <- as.vector(t(leftrightmat))
ans <- raw_ans[!is.na(raw_ans)]
return(ans[1:n])
}
thingfinder(A=c(1,3,NA,3,NA,4,NA,1,7,NA,2,NA,9,9,10), R=3, t=5, n=3)
## [1] 3 4 3
这当然会优先考虑左侧。
一个相对简短的解决方案是:
orderedA <- A[order(abs(seq_len(length(A)) - t))][seq_len(R*2)]
n_obj <- min(sum(is.na(orderedA)), N, length(na.omit(orderedA)))
res <- na.omit(orderedA)[seq_len(n_obj)]
res
#[1] 3 4 3
进一步分解步骤如下:
顺序A,通过与感兴趣位置的绝对距离,
t
。- 代码为:
A[order(abs(seq_len(length(A)) - t))]
- 代码为:
子集到第一个
R*2
元素(因此这将得到R
内t
两侧的元素。- 代码为:
[seq_len(R*2)]
- 代码为:
- 获取第
min(N, # of non-NA, len of non-NA)
个元素- 代码为:
min(sum(is.na(orderedA)), N, length(na.omit(orderedA)))
- 代码为:
- 放弃
NA
- 代码为:
na.omit()
- 代码为:
- 取第3步中确定的第一个元素(以较小者为准)
- 代码为:
[seq_len(n_obj)]
- 代码为:
如果对其他人有帮助,@Mike H. 还为我提供了 return 与所需向量元素相关联的索引 positions
的解决方案 res
:
A <- setNames(A, seq_len(length(A)))
orderedA <- A[order(abs(seq_len(length(A)) - t))][seq_len(R*2)]
n_obj <- min(sum(is.na(orderedA)), N, length(na.omit(orderedA)))
res <- na.omit(orderedA)[seq_len(n_obj)]
positions <- as.numeric(names(res))