我遇到一个关于“下标越界”的问题,我想要的是获得每个观察的第一个和最后一个月,我有三个连续的“1”或“真”。我想创建2个新列“开始”和“结束”,我分别在第一个月和最后一个月。 在我的第一次观察的例子中:开始等于艾薇儿,结束等于juin 在5观察中:开始等于fevrier,结束等于avril 在9观察中:开始等于janvier,结束等于火星 ...
我试着这样做:
nom <- letters[1:5]
pseudo <- paste(name, 21:25, sep = "")
janvier <- c(0, 1, 1, 1, 0)
fevrier <- c(1, 1, 1, 1, 1)
mars <- c(0, 0, 0, 1, 1)
avril <- c(1, 1, 1, 0, 1)
mai <- c(1, 0, 1, 1, 1)
juin <- c(1, 1, 0, 1, 0)
df <- data.frame(nom =nom, pseudo = pseudo, janvier = janvier,
fevrier = fevrier, mars = mars, avril = avril,
mai = mai, juin = juin)
dfm <- as.matrix(df[, -c(1, 2)])
my_matrix <- matrix(nrow = 10, ncol = 6)
for(i in 1:dim(dfm)[1]){
for(j in 1:dim(dfm)[2]){
if(dfm[i, j] + dfm[i, j+1] + dfm[i, j+2] == 3){
my_matrix[i, j] <- "periode_ok"
my_matrix[i, j+1] <- "periode_ok"
my_matrix[i, j+2] <- "periode_ok"
}
}
}
输出应为:
begin <- c("avril", "no info", "no info",
"janvier", "fevrier", "avril", "no info",
"no info", "janvier", "fevrier")
end <- c("juin", "no info", "no info", "mars",
"avril", "juin", "no info", "no info",
"mars", "avril")
output <- data.frame(nom =nom, pseudo = pseudo, janvier = janvier,
fevrier = fevrier, mars = mars, avril = avril,
mai = mai, juin = juin, begin = begin,end = end)
任何帮助都将是apreciated
答案 0 :(得分:4)
首先,像1:dim(dfm)[1]
这样的结构是危险的,因为如果dim(dfm)[1]
为零,您将获得完全有效的向量1:0
,并且循环将尝试解决向量的元素零或在这种情况下,矩阵。这是非法的,会引发错误。建议的解决方案是使用seq_len(...)
。
其次,我使用dim(dfm)[.]
和nrow
代替ncol
。
现在你已经得到了错误。您正在尝试处理列j + 1
和j + 2
,因此当j
到达ncol(dfm)
时,您已脱离债券。下面的代码删除了循环限制的最后两个元素。
n <- ncol(dfm)
for(i in seq_len(nrow(dfm))){
for(j in seq_len(n)[-c(n - 1, n)]){
if(dfm[i, j] + dfm[i, j+1] + dfm[i, j+2] == 3){
my_matrix[i, j] <- "periode_ok"
my_matrix[i, j+1] <- "periode_ok"
my_matrix[i, j+2] <- "periode_ok"
}
}
}
my_matrix
答案 1 :(得分:2)
当然有一个矢量化解决方案,但是如果你想纠正你的for循环,你需要将j
限制为dfm
减去2的维度,因为你要检查前面的两列。根据您提供的内容,这将有助于您;但是,目前尚不清楚如何从5行df
获得10行(重复两次)。
my_matrix <- matrix("no info", nrow = 5, ncol = 2)
colnames(my_matrix) <- c("begin", "end")
for(i in 1:dim(dfm)[1]){
for(j in 1:(dim(dfm)[2]-2)){
if(dfm[i, j] + dfm[i, j+1] + dfm[i, j+2] == 3){
my_matrix[i, 1] <- colnames(dfm)[j]
my_matrix[i, 2] <- colnames(dfm)[j+2]
break
}
}
}
output <- cbind(df, my_matrix)
然后结果将是:
output
# nom pseudo janvier fevrier mars avril mai juin begin end
# 1 a name21 0 1 0 1 1 1 avril juin
# 2 b name22 1 1 0 1 0 1 no info no info
# 3 c name23 1 1 0 1 1 0 no info no info
# 4 d name24 1 1 1 0 1 1 janvier mars
# 5 e name25 0 1 1 1 1 0 fevrier avril