use of dr.inference.loggers.Loggable in project beast-mcmc by beast-dev.
the class TreeLoggerParser method parseXMLParameters.
protected void parseXMLParameters(XMLObject xo) throws XMLParseException {
// reset this every time...
branchRates = null;
tree = (Tree) xo.getChild(Tree.class);
title = xo.getAttribute(TITLE, "");
nexusFormat = xo.getAttribute(NEXUS_FORMAT, false);
sortTranslationTable = xo.getAttribute(SORT_TRANSLATION_TABLE, true);
boolean substitutions = xo.getAttribute(BRANCH_LENGTHS, "").equals(SUBSTITUTIONS);
List<TreeAttributeProvider> taps = new ArrayList<TreeAttributeProvider>();
List<TreeTraitProvider> ttps = new ArrayList<TreeTraitProvider>();
// ttps2 are for TTPs that are not specified within a Trait element. These are only
// included if not already added through a trait element to avoid duplication of
// (in particular) the BranchRates which is required for substitution trees.
List<TreeTraitProvider> ttps2 = new ArrayList<TreeTraitProvider>();
for (int i = 0; i < xo.getChildCount(); i++) {
Object cxo = xo.getChild(i);
if (cxo instanceof Likelihood) {
final Likelihood likelihood = (Likelihood) cxo;
taps.add(new TreeAttributeProvider() {
public String[] getTreeAttributeLabel() {
return new String[] { "lnP" };
}
public String[] getAttributeForTree(Tree tree) {
return new String[] { Double.toString(likelihood.getLogLikelihood()) };
}
});
}
if (cxo instanceof TreeAttributeProvider) {
taps.add((TreeAttributeProvider) cxo);
}
if (cxo instanceof TreeTraitProvider) {
if (xo.hasAttribute(FILTER_TRAITS)) {
String[] matches = ((String) xo.getAttribute(FILTER_TRAITS)).split("[\\s,]+");
TreeTraitProvider ttp = (TreeTraitProvider) cxo;
TreeTrait[] traits = ttp.getTreeTraits();
List<TreeTrait> filteredTraits = new ArrayList<TreeTrait>();
for (String match : matches) {
for (TreeTrait trait : traits) {
if (trait.getTraitName().startsWith(match)) {
filteredTraits.add(trait);
}
}
}
if (filteredTraits.size() > 0) {
ttps2.add(new TreeTraitProvider.Helper(filteredTraits));
}
} else {
// Add all of them
ttps2.add((TreeTraitProvider) cxo);
}
}
if (cxo instanceof XMLObject) {
XMLObject xco = (XMLObject) cxo;
if (xco.getName().equals(TREE_TRAIT)) {
TreeTraitProvider ttp = (TreeTraitProvider) xco.getChild(TreeTraitProvider.class);
if (xco.hasAttribute(NAME)) {
// a specific named trait is required (optionally with a tag to name it in the tree file)
String name = xco.getStringAttribute(NAME);
final TreeTrait trait = ttp.getTreeTrait(name);
if (trait == null) {
String childName = "TreeTraitProvider";
if (ttp instanceof Likelihood) {
childName = ((Likelihood) ttp).prettyName();
} else if (ttp instanceof Model) {
childName = ((Model) ttp).getModelName();
}
throw new XMLParseException("Trait named, " + name + ", not found for " + childName);
}
final String tag;
if (xco.hasAttribute(TAG)) {
tag = xco.getStringAttribute(TAG);
} else {
tag = name;
}
ttps.add(new TreeTraitProvider.Helper(tag, new TreeTrait() {
public String getTraitName() {
return tag;
}
public Intent getIntent() {
return trait.getIntent();
}
public Class getTraitClass() {
return trait.getTraitClass();
}
public Object getTrait(Tree tree, NodeRef node) {
return trait.getTrait(tree, node);
}
public String getTraitString(Tree tree, NodeRef node) {
return trait.getTraitString(tree, node);
}
public boolean getLoggable() {
return trait.getLoggable();
}
}));
} else if (xo.hasAttribute(FILTER_TRAITS)) {
// else a filter attribute is given to ask for all traits that starts with a specific
// string
String[] matches = ((String) xo.getAttribute(FILTER_TRAITS)).split("[\\s,]+");
TreeTrait[] traits = ttp.getTreeTraits();
List<TreeTrait> filteredTraits = new ArrayList<TreeTrait>();
for (String match : matches) {
for (TreeTrait trait : traits) {
if (trait.getTraitName().startsWith(match)) {
filteredTraits.add(trait);
}
}
}
if (filteredTraits.size() > 0) {
ttps.add(new TreeTraitProvider.Helper(filteredTraits));
}
} else {
// neither named or filtered traits so just add them all
ttps.add(ttp);
}
}
}
// be able to put arbitrary statistics in as tree attributes
if (cxo instanceof Loggable) {
final Loggable loggable = (Loggable) cxo;
taps.add(new TreeAttributeProvider() {
public String[] getTreeAttributeLabel() {
String[] labels = new String[loggable.getColumns().length];
for (int i = 0; i < loggable.getColumns().length; i++) {
labels[i] = loggable.getColumns()[i].getLabel();
}
return labels;
}
public String[] getAttributeForTree(Tree tree) {
String[] values = new String[loggable.getColumns().length];
for (int i = 0; i < loggable.getColumns().length; i++) {
values[i] = loggable.getColumns()[i].getFormatted();
}
return values;
}
});
}
}
// inclusion of the codon partitioned robust counting TTP...
if (ttps2.size() > 0) {
ttps.addAll(ttps2);
}
if (substitutions) {
branchRates = (BranchRates) xo.getChild(BranchRates.class);
}
if (substitutions && branchRates == null) {
throw new XMLParseException("To log trees in units of substitutions a BranchRateModel must be provided");
}
// logEvery of zero only displays at the end
logEvery = xo.getAttribute(LOG_EVERY, 0);
// double normaliseMeanRateTo = xo.getAttribute(NORMALISE_MEAN_RATE_TO, Double.NaN);
// decimal places
final int dp = xo.getAttribute(DECIMAL_PLACES, -1);
if (dp != -1) {
format = NumberFormat.getNumberInstance(Locale.ENGLISH);
format.setMaximumFractionDigits(dp);
}
final PrintWriter pw = getLogFile(xo, getParserName());
formatter = new TabDelimitedFormatter(pw);
treeAttributeProviders = new TreeAttributeProvider[taps.size()];
taps.toArray(treeAttributeProviders);
treeTraitProviders = new TreeTraitProvider[ttps.size()];
ttps.toArray(treeTraitProviders);
// I think the default should be to have names rather than numbers, thus the false default - AJD
// I think the default should be numbers - using names results in larger files and end user never
// sees the numbers anyway as any software loading the nexus files does the translation - JH
mapNames = xo.getAttribute(MAP_NAMES, true);
condition = logEvery == 0 ? (TreeLogger.LogUpon) xo.getChild(TreeLogger.LogUpon.class) : null;
}
Aggregations