[Phylobase-commits] r647 - pkg/R
noreply at r-forge.r-project.org
noreply at r-forge.r-project.org
Sun Sep 13 21:04:58 CEST 2009
Author: regetz
Date: 2009-09-13 21:04:58 +0200 (Sun, 13 Sep 2009)
New Revision: 647
Modified:
pkg/R/subset.R
Log:
fixed subset's sensitivity to tip.label order (bug #643); enhanced error
handling; reformatted to standard R indentation since most lines were
modified anyway
Modified: pkg/R/subset.R
===================================================================
--- pkg/R/subset.R 2009-09-12 18:52:03 UTC (rev 646)
+++ pkg/R/subset.R 2009-09-13 19:04:58 UTC (rev 647)
@@ -3,64 +3,66 @@
################
setGeneric("subset")
-setMethod("subset", "phylo4",
- function(x,tips.include=NULL,tips.exclude=NULL,
- mrca=NULL,node.subtree=NULL,...) {
- ## FIXME: could eliminate NULL and make the test
- ## if (!missing) rather than if (!is.null)
- ## (might have to change next line?)
- if (sum(!sapply(list(tips.include,tips.exclude,
- mrca,node.subtree),is.null))>1) {
- stop("must specify at most one criterion for subsetting")
- }
- #arglist <- list(...)
- #if (length(arglist)>0) {
- # warning("unused arguments: ",
- # paste(names(arglist),collapse=","))
- #}
- kept <- x at tip.label
- dropped <- character(0)
- if (!is.null(tips.include)) {
- if (is.numeric(tips.include)) {
- tips.include <- x at tip.label[tips.include]
- }
- unknown <- setdiff(tips.include,x at tip.label)
- if (length(unknown)>0) {
- warning("unknown tip labels ignored:",
- paste(unknown,collapse=", "))
- tips.include <- intersect(tips.include,x at tip.label)
- }
- kept <- tips.include
- dropped <- setdiff(x at tip.label,tips.include)
- }
- if (!is.null(tips.exclude)) {
- if (is.numeric(tips.exclude)) {
- tips.exclude <- x at tip.label[tips.exclude]
- }
- unknown <- setdiff(tips.exclude,x at tip.label)
- if (length(unknown)>0) {
- warning("unknown tip labels ignored:",
- paste(unknown,collapse=", "))
- tips.exclude <- intersect(tips.exclude,x at tip.label)
- }
- dropped <- tips.exclude
- kept <- setdiff(x at tip.label,tips.exclude)
- }
- if (!is.null(node.subtree)) {
- kept <- intersect(x at tip.label,names(descendants(x,node.subtree)))
- dropped <- setdiff(x at tip.label,kept)
- }
- if (!is.null(mrca)) {
- mnode <- MRCA(x,mrca)
- kept <- intersect(x at tip.label,names(descendants(x,mnode)))
- dropped <- setdiff(x at tip.label,kept)
- }
- if (length(kept)<2) {
- stop("0 or 1 tips would remain after subsetting")
- }
- if (length(dropped)==0) return(x)
- return(prune(x, dropped, ...))
- })
+setMethod("subset", "phylo4", function(x, tips.include=NULL,
+ tips.exclude=NULL, mrca=NULL, node.subtree=NULL, ...) {
+ ## FIXME: could eliminate NULL and make the test
+ ## if (!missing) rather than if (!is.null)
+ ## (might have to change next line?)
+ if (sum(!sapply(list(tips.include, tips.exclude, mrca,
+ node.subtree), is.null))>1) {
+ stop("must specify at most one criterion for subsetting")
+ }
+ #arglist <- list(...)
+ #if (length(arglist)>0) {
+ # warning("unused arguments: ",
+ # paste(names(arglist),collapse=","))
+ #}
+ all.tips <- nodeId(x, "tip")
+ if (!is.null(tips.include)) {
+ nodes <- getNode(x, tips.include, missing="OK")
+ is.valid.tip <- nodes %in% all.tips
+ kept <- nodes[is.valid.tip]
+ dropped <- setdiff(all.tips, kept)
+ unknown <- tips.include[!is.valid.tip]
+ } else if (!is.null(tips.exclude)) {
+ nodes <- getNode(x, tips.exclude, missing="OK")
+ is.valid.tip <- nodes %in% all.tips
+ dropped <- nodes[is.valid.tip]
+ kept <- setdiff(all.tips, dropped)
+ unknown <- tips.exclude[!is.valid.tip]
+ } else if (!is.null(mrca)) {
+ nodes <- getNode(x, mrca, missing="OK")
+ is.valid.tip <- nodes %in% all.tips
+ if (sum(is.valid.tip)<2) {
+ stop("mrca must include at least two valid tips")
+ }
+ mnode <- MRCA(x, nodes[is.valid.tip])
+ kept <- descendants(x, mnode)
+ dropped <- setdiff(all.tips, kept)
+ unknown <- mrca[!is.valid.tip]
+ } else if (!is.null(node.subtree)) {
+ node <- getNode(x, node.subtree, missing="OK")
+ if (length(node)!=1 || !(node %in% nodeId(x, "internal"))) {
+ stop("node.subtree must be a single valid internal node")
+ }
+ kept <- descendants(x, node)
+ dropped <- setdiff(all.tips, kept)
+ unknown <- numeric(0)
+ } else {
+ kept <- x at tip.label
+ dropped <- numeric(0)
+ unknown <- numeric(0)
+ }
+ if (length(unknown)>0) {
+ warning("unknown tips ignored: ", paste(unknown,
+ collapse=", "))
+ }
+ if (length(kept)<2) {
+ stop("0 or 1 tips would remain after subsetting")
+ }
+ if (length(dropped)==0) return(x)
+ return(prune(x, dropped, ...))
+})
###############
# '[' operator
More information about the Phylobase-commits
mailing list