org.biojavax.bio.phylo.io.nexus.DistancesBlock Maven / Gradle / Ivy
/*
* BioJava development code
*
* This code may be freely distributed and modified under the
* terms of the GNU Lesser General Public Licence. This should
* be distributed with the code. If you do not have a copy,
* see:
*
* http://www.gnu.org/copyleft/lesser.html
*
* Copyright for this code is held jointly by the individual
* authors. These should be listed in @author doc comments.
*
* For more information on the BioJava project and its aims,
* or to join the biojava-l mailing list, visit the home page
* at:
*
* http://www.biojava.org/
*
*/
package org.biojavax.bio.phylo.io.nexus;
import java.io.IOException;
import java.io.Writer;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import org.biojava.bio.seq.io.ParseException;
/**
* Represents Nexus distances blocks.
*
* @author Richard Holland
* @author Tobias Thierer
* @author Jim Balhoff
* @since 1.6
*/
public class DistancesBlock extends NexusBlock.Abstract {
/**
* A constant representing the name of Distances blocks.
*/
public static final String DISTANCES_BLOCK = "DISTANCES";
private int dimensionsNTax = 0;
private int dimensionsNChar = 0;
private String triangle = "LOWER";
private boolean diagonal = true;
private boolean labels = true;
private String missing = "?";
private boolean interleaved = false;
private List taxLabels = new ArrayList();
// values are lists, containing strings and nulls which are gaps
private Map matrix = new LinkedHashMap();
private List comments = new ArrayList();
/**
* Delegates to NexusBlock.Abstract constructor using
* DistancesBlock.DISTANCES_BLOCK as the name.
*/
public DistancesBlock() {
super(DistancesBlock.DISTANCES_BLOCK);
}
/**
* Set the NTAX value.
*
* @param dimensionsNTax
* the NTAX value.
*/
public void setDimensionsNTax(int dimensionsNTax) {
this.dimensionsNTax = dimensionsNTax;
}
/**
* Get the NTAX value.
*
* @return the NTAX value.
*/
public int getDimensionsNTax() {
return this.dimensionsNTax;
}
/**
* Set the NCHAR value.
*
* @param dimensionsNChar
* the NCHAR value.
*/
public void setDimensionsNChar(int dimensionsNChar) {
this.dimensionsNChar = dimensionsNChar;
}
/**
* Get the NCHAR value.
*
* @return the NCHAR value.
*/
public int getDimensionsNChar() {
return this.dimensionsNChar;
}
public void setTriangle(final String triangle) {
this.triangle = triangle;
}
public void setDiagonal(final boolean diagonal) {
this.diagonal = diagonal;
}
public boolean isDiagonal() {
return this.diagonal;
}
public void setLabels(final boolean labels) {
this.labels = labels;
}
public boolean isLabels() {
return this.labels;
}
public void setMissing(final String missing) {
this.missing = missing;
}
public String getMissing() {
return this.missing;
}
public void setInterleaved(final boolean interleaved) {
this.interleaved = interleaved;
}
public boolean isInterleaved() {
return this.interleaved;
}
/**
* Add a TAXLABEL. If it already exists, or is a number that refers to an
* index position that already exists, an exception is thrown.
*
* @param taxLabel
* the label to add.
* @throws ParseException
* if the label cannot be added.
*/
public void addTaxLabel(final String taxLabel) throws ParseException {
if (this.taxLabels.contains(taxLabel))
throw new ParseException("Duplicate taxa label: " + taxLabel);
else
try {
// Try it as a number to see if it refers to
// position we already have.
final int i = Integer.parseInt(taxLabel);
if (i <= this.taxLabels.size() + 1)
throw new ParseException("Taxa label " + i
+ " refers to already extant taxa position");
} catch (NumberFormatException e) {
// It is not a number, so ignore.
} catch (ParseException e) {
// Throw it.
throw e;
}
this.taxLabels.add(taxLabel);
}
/**
* Removes the given TAXLABEL.
*
* @param taxLabel
* the label to remove.
*/
public void removeTaxLabel(final String taxLabel) {
this.taxLabels.remove(taxLabel);
}
/**
* Checks to see if we contain the given TAXLABEL.
*
* @param taxLabel
* the label to check for.
* @return true if we already contain it.
*/
public boolean containsTaxLabel(final String taxLabel) {
if (this.taxLabels.contains(taxLabel))
return true;
else
try {
// Try it as a number to see if it refers to
// position we already have.
final int i = Integer.parseInt(taxLabel);
if (i <= this.taxLabels.size() + 1)
return true;
} catch (NumberFormatException e) {
// It is not a number, so ignore.
}
return false;
}
/**
* Get the TAXLABEL values added so far.
*
* @return this labels so far.
*/
public List getTaxLabels() {
return this.taxLabels;
}
public void addMatrixEntry(final String taxa) {
if (!this.matrix.containsKey(taxa))
this.matrix.put(taxa, new ArrayList());
}
public void appendMatrixData(final String taxa, final Object data) {
((List) this.matrix.get(taxa)).add(data);
}
public List getMatrixData(final String taxa) {
return (List) this.matrix.get(taxa);
}
public Collection getMatrixLabels() {
return Collections.unmodifiableSet(this.matrix.keySet());
}
/**
* Adds a comment.
*
* @param comment
* the comment to add.
*/
public void addComment(final NexusComment comment) {
this.comments.add(comment);
}
/**
* Removes a comment.
*
* @param comment
* the comment to remove.
*/
public void removeComment(final NexusComment comment) {
this.comments.remove(comment);
}
/**
* Returns all comments.
*
* @return all the selected comments.
*/
public List getComments() {
return this.comments;
}
protected void writeBlockContents(Writer writer) throws IOException {
for (final Iterator i = this.comments.iterator(); i.hasNext();) {
((NexusComment) i.next()).writeObject(writer);
writer.write(NexusFileFormat.NEW_LINE);
}
writer.write(" DIMENSIONS ");
if (!this.taxLabels.isEmpty())
writer.write("NEWTAXA ");
if (this.dimensionsNTax > 0)
writer.write("NTAX=" + this.dimensionsNTax + " ");
writer.write("NCHAR=" + this.dimensionsNChar + ";"
+ NexusFileFormat.NEW_LINE);
writer.write(" FORMAT TRIANGLE=");
this.writeToken(writer, this.triangle);
writer.write(this.diagonal ? " DIAGONAL" : " NODIAGONAL");
writer.write(this.labels ? " LABELS" : " NOLABELS");
writer.write(" MISSING=");
this.writeToken(writer, this.missing);
if (this.interleaved)
writer.write(" INTERLEAVED");
writer.write(";" + NexusFileFormat.NEW_LINE);
if (this.taxLabels.size() > 0) {
writer.write(" TAXLABELS");
for (final Iterator i = this.taxLabels.iterator(); i.hasNext();) {
writer.write(' ');
this.writeToken(writer, (String) i.next());
}
writer.write(";" + NexusFileFormat.NEW_LINE);
}
// if statesformat=statespresent and items=1, bracket only multi values,
// otherwise bracket all values
// only space tokens if reallyUseTokens=true
writer.write(" MATRIX" + NexusFileFormat.NEW_LINE);
for (final Iterator i = this.matrix.entrySet().iterator(); i.hasNext();) {
final Map.Entry entry = (Map.Entry) i.next();
writer.write('\t');
this.writeToken(writer, "" + entry.getKey());
writer.write('\t');
for (final Iterator j = ((List) entry.getValue()).iterator(); j
.hasNext();) {
final Object obj = j.next();
if (obj instanceof String)
this.writeToken(writer, (String) obj);
if (j.hasNext())
writer.write('\t');
}
writer.write(NexusFileFormat.NEW_LINE);
}
writer.write(";" + NexusFileFormat.NEW_LINE);
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy