从列表中删除重复和小向量

时间:2015-06-16 13:31:40

标签: r

我有一个载体列表,比如说:

li <- list( c(1, 2, 3),
            c(1, 2, 3, 4),
            c(2, 3, 4),
            c(5, 6, 7, 8, 9, 10, 11, 12),
            numeric(0),
            c(5, 6, 7, 8, 9, 10, 11, 12, 13)
            )

我想删除其他已经包含的所有向量(更大或相等),以及所有空向量

在这种情况下,我只剩下列表

1 2 3 4
5  6  7  8  9 10 11 12 13

是否有任何有用的功能来实现这一目标?

提前致谢

2 个答案:

答案 0 :(得分:2)

首先,您应该按照向量长度对列表进行排序,这样在切除循环中可以保证每个低索引向量都比每个高索引向量短,所以单向setdiff()就是你的全部需要。

l <- list(1:3, 1:4, 2:4, 5:12, double(), 5:13 );
ls <- l[order(sapply(l,length))];
i <- 1; while (i <= length(ls)-1) if (length(ls[[i]]) == 0 || any(sapply((i+1):length(ls),function(i2) length(setdiff(ls[[i]],ls[[i2]]))) == 0)) ls[[i]] <- NULL else i <- i+1;
ls;
## [[1]]
## [1] 1 2 3 4
##
## [[2]]
## [1]  5  6  7  8  9 10 11 12 13

这是一个轻微的替代方案,用第二个while循环替换any(sapply(...))。优点是如果在列表的其余部分中找到任何超集,则while循环可能会过早中断。

l <- list(1:3, 1:4, 2:4, 5:12, double(), 5:13 );
ls <- l[order(sapply(l,length))];
i <- 1; while (i <= length(ls)-1) if (length(ls[[i]]) == 0 || { j <- i+1; res <- F; while (j <= length(ls)) if (length(setdiff(ls[[i]],ls[[j]])) == 0) { res <- T; break; } else j <- j+1; res; }) ls[[i]] <- NULL else i <- i+1;
ls;
## [[1]]
## [1] 1 2 3 4
##
## [[2]]
## [1]  5  6  7  8  9 10 11 12 13

答案 1 :(得分:0)

如果

,则包含在y中
length(setdiff(x, y)) == 0

您可以使用expand.grid或combn等函数将它应用于每对向量。