如何使用 repeat、while 循环或其他迭代技术根据某些规则编写 returns 输入向量索引的函数
How to write a function that returns indexes of input vector according to some rules, using repeat, while loop, or other iteration technique
我正在尝试编写一个将数字向量作为输入的函数,并且 return 是输入向量的较短版本的 indexes,根据一些规则:
(a) 如果所有元素都相同,return只是第一个元素的index;即 return 1
;否则:
如果不是所有元素都相同,则测试 special_treatment_value
是否在其中:
- (b) 如果
special_treatment_value
存在,return 输入向量的 索引 除了 special_treatment_value
出现的元素的索引;否则:
- (c) 如果
special_treatment_value
不存在,则 return 按原样输入向量的索引,即 1:length(x)
.
问题:如果我们在路线(b)中结束,我们可能会遇到所有矢量元素现在都相同的情况。在这种情况下,我们想再次遍历 (a) 以最小化到第一个元素。
例子
假设我想通过我的函数传递以下向量:
my_vec_1 <- c(1, 2, 1, 2, 3)
my_vec_2 <- c(4, 4, 4)
my_vec_3 <- c(1, 2, 1, 4, 1)
my_vec_4 <- c(3, 3, 3, 4)
还有那个:
special_treatment_value <- 4
根据我的规则,函数应该 return 输出:
- 对于
my_vec_1
:它适合路线(c)因此输出应该是1:5
(所有的索引)
- for
my_vec_2
:它适合路线 (a) 因此输出应该是 1
(第一个索引)
- for
my_vec_3
:适合路线(b)。输出应为 1 2 3 5
(除特殊值外的所有索引)
my_vec_4
演示了问题。我想要的输出是 1
因为首先我们通过路线 (b) 然后 我希望 通过 (a)。但现在它没有发生,我的功能(见下文)returns 1 2 3
(除特殊值外的所有索引)。
我目前的尝试
get_indexes <- function(x, special_val) {
if (var(x) == 0) { # route (a)
output_idx <- 1
return(output_idx)
}
idx_entire_length <- 1:length(x)
if (any(x == special_val)) { # route (b)
idx_to_remove <- which(x == special_val)
output_idx <- idx_entire_length[-idx_to_remove]
return(output_idx)
}
# else
output_idx <- idx_entire_length # route (c)
return(output_idx)
}
get_indexes(my_vec_1, 4)
#> [1] 1 2 3 4 5
get_indexes(my_vec_2, 4)
#> [1] 1
get_indexes(my_vec_3, 4)
#> [1] 1 2 3 5
get_indexes(my_vec_4, 4)
#> [1] 1 2 3
我想应该有一些 repeat
块或 while
循环,但我不知道如何正确(有效)地实现它。
您可以在条件 (b) 中重复通过 (a) 的条件,例如:
f <- function(x, treatment){
if(var(x) == 0) 1 else {
if(treatment %in% x) {
x[-which(x == treatment)] |>
(\(.) if(var(.) == 0) 1 else (1:length(x))[-which(x == treatment)])()
} else {
1:length(x)
}
}
}
lapply(list(v1, v2, v3, v4), f, 4)
[[1]]
[1] 1 2 3 4 5
[[2]]
[1] 1
[[3]]
[1] 1 2 3 5
[[4]]
[1] 1
你可以试试
foo <- function(x, y){
tmp <- which(x != y)
if(dplyr::n_distinct(x[x!=y])<=1){
tmp <- 1
}
return(tmp)
}
相反 n_distinct()
你可以使用 length(unique())
结果:
lapply(list(my_vec_1, my_vec_2, my_vec_3, my_vec_4), foo, 4)
[[1]]
[1] 1 2 3 4 5
[[2]]
[1] 1
[[3]]
[1] 1 2 3 5
[[4]]
[1] 1
我正在尝试编写一个将数字向量作为输入的函数,并且 return 是输入向量的较短版本的 indexes,根据一些规则:
(a) 如果所有元素都相同,return只是第一个元素的index;即 return
1
;否则:如果不是所有元素都相同,则测试
special_treatment_value
是否在其中:- (b) 如果
special_treatment_value
存在,return 输入向量的 索引 除了special_treatment_value
出现的元素的索引;否则: - (c) 如果
special_treatment_value
不存在,则 return 按原样输入向量的索引,即1:length(x)
.
- (b) 如果
问题:如果我们在路线(b)中结束,我们可能会遇到所有矢量元素现在都相同的情况。在这种情况下,我们想再次遍历 (a) 以最小化到第一个元素。
例子
假设我想通过我的函数传递以下向量:
my_vec_1 <- c(1, 2, 1, 2, 3)
my_vec_2 <- c(4, 4, 4)
my_vec_3 <- c(1, 2, 1, 4, 1)
my_vec_4 <- c(3, 3, 3, 4)
还有那个:
special_treatment_value <- 4
根据我的规则,函数应该 return 输出:
- 对于
my_vec_1
:它适合路线(c)因此输出应该是1:5
(所有的索引) - for
my_vec_2
:它适合路线 (a) 因此输出应该是1
(第一个索引) - for
my_vec_3
:适合路线(b)。输出应为1 2 3 5
(除特殊值外的所有索引) my_vec_4
演示了问题。我想要的输出是1
因为首先我们通过路线 (b) 然后 我希望 通过 (a)。但现在它没有发生,我的功能(见下文)returns1 2 3
(除特殊值外的所有索引)。
我目前的尝试
get_indexes <- function(x, special_val) {
if (var(x) == 0) { # route (a)
output_idx <- 1
return(output_idx)
}
idx_entire_length <- 1:length(x)
if (any(x == special_val)) { # route (b)
idx_to_remove <- which(x == special_val)
output_idx <- idx_entire_length[-idx_to_remove]
return(output_idx)
}
# else
output_idx <- idx_entire_length # route (c)
return(output_idx)
}
get_indexes(my_vec_1, 4)
#> [1] 1 2 3 4 5
get_indexes(my_vec_2, 4)
#> [1] 1
get_indexes(my_vec_3, 4)
#> [1] 1 2 3 5
get_indexes(my_vec_4, 4)
#> [1] 1 2 3
我想应该有一些 repeat
块或 while
循环,但我不知道如何正确(有效)地实现它。
您可以在条件 (b) 中重复通过 (a) 的条件,例如:
f <- function(x, treatment){
if(var(x) == 0) 1 else {
if(treatment %in% x) {
x[-which(x == treatment)] |>
(\(.) if(var(.) == 0) 1 else (1:length(x))[-which(x == treatment)])()
} else {
1:length(x)
}
}
}
lapply(list(v1, v2, v3, v4), f, 4)
[[1]]
[1] 1 2 3 4 5
[[2]]
[1] 1
[[3]]
[1] 1 2 3 5
[[4]]
[1] 1
你可以试试
foo <- function(x, y){
tmp <- which(x != y)
if(dplyr::n_distinct(x[x!=y])<=1){
tmp <- 1
}
return(tmp)
}
相反 n_distinct()
你可以使用 length(unique())
结果:
lapply(list(my_vec_1, my_vec_2, my_vec_3, my_vec_4), foo, 4)
[[1]]
[1] 1 2 3 4 5
[[2]]
[1] 1
[[3]]
[1] 1 2 3 5
[[4]]
[1] 1