X-Git-Url: http://source.jalview.org/gitweb/?a=blobdiff_plain;f=src%2Fjalview%2Fanalysis%2FNJTree.java;h=44897838dfc57abdd44af3252b620457caa3c9a9;hb=4d7f98a6dd54d9863ba449ec79dcd95d25ed863d;hp=2fe85977b28d1ba9f953694a11c27780abd2ed4c;hpb=6cfa5983e39db21e566e8662722d231f5391e057;p=jalview.git diff --git a/src/jalview/analysis/NJTree.java b/src/jalview/analysis/NJTree.java old mode 100755 new mode 100644 index 2fe8597..4489783 --- a/src/jalview/analysis/NJTree.java +++ b/src/jalview/analysis/NJTree.java @@ -1,29 +1,40 @@ /* - * Jalview - A Sequence Alignment Editor and Viewer (Development Version 2.4.1) - * Copyright (C) 2009 AM Waterhouse, J Procter, G Barton, M Clamp, S Searle + * Jalview - A Sequence Alignment Editor and Viewer ($$Version-Rel$$) + * Copyright (C) $$Year-Rel$$ The Jalview Authors * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License - * as published by the Free Software Foundation; either version 2 - * of the License, or (at your option) any later version. + * This file is part of Jalview. * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. + * Jalview is free software: you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation, either version 3 + * of the License, or (at your option) any later version. + * + * Jalview is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty + * of MERCHANTABILITY or FITNESS FOR A PARTICULAR + * PURPOSE. See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA + * along with Jalview. If not, see . + * The Jalview Authors are detailed in the 'AUTHORS' file. */ package jalview.analysis; -import java.util.*; - -import jalview.datamodel.*; -import jalview.io.*; -import jalview.schemes.*; -import jalview.util.*; +import jalview.api.analysis.ScoreModelI; +import jalview.datamodel.AlignmentView; +import jalview.datamodel.BinaryNode; +import jalview.datamodel.CigarArray; +import jalview.datamodel.NodeTransformI; +import jalview.datamodel.SeqCigar; +import jalview.datamodel.Sequence; +import jalview.datamodel.SequenceI; +import jalview.datamodel.SequenceNode; +import jalview.io.NewickFile; +import jalview.schemes.ResidueProperties; + +import java.util.Enumeration; +import java.util.List; +import java.util.Vector; /** * DOCUMENT ME! @@ -90,11 +101,11 @@ public class NJTree * and original alignment data represented by Cigar strings. * * @param seqs - * SequenceI[] + * SequenceI[] * @param odata - * Cigar[] + * Cigar[] * @param treefile - * NewickFile + * NewickFile */ public NJTree(SequenceI[] seqs, AlignmentView odata, NewickFile treefile) { @@ -115,9 +126,9 @@ public class NJTree * Creates a new NJTree object from a tree from an external source * * @param seqs - * SequenceI which should be associated with leafs of treefile + * SequenceI which should be associated with leafs of treefile * @param treefile - * A parsed tree + * A parsed tree */ public NJTree(SequenceI[] seqs, NewickFile treefile) { @@ -196,18 +207,18 @@ public class NJTree * Creates a new NJTree object. * * @param sequence - * DOCUMENT ME! + * DOCUMENT ME! * @param type - * DOCUMENT ME! + * DOCUMENT ME! * @param pwtype - * DOCUMENT ME! + * DOCUMENT ME! * @param start - * DOCUMENT ME! + * DOCUMENT ME! * @param end - * DOCUMENT ME! + * DOCUMENT ME! */ public NJTree(SequenceI[] sequence, AlignmentView seqData, String type, - String pwtype, int start, int end) + String pwtype, ScoreModelI sm, int start, int end) { this.sequence = sequence; this.node = new Vector(); @@ -228,17 +239,17 @@ public class NJTree sdata.addOperation(CigarArray.M, end - start + 1); this.seqData = new AlignmentView(sdata, start); } -// System.err.println("Made seqData");// dbg + // System.err.println("Made seqData");// dbg if (!(type.equals("NJ"))) { type = "AV"; } - if (!(pwtype.equals("PID"))) + if (sm == null && !(pwtype.equals("PID"))) { if (ResidueProperties.getScoreMatrix(pwtype) == null) { - type = "BLOSUM62"; + pwtype = "BLOSUM62"; } } @@ -254,39 +265,39 @@ public class NJTree noseqs = i++; - distance = findDistances(this.seqData - .getSequenceStrings(Comparison.GapChars.charAt(0))); -// System.err.println("Made distances");// dbg + distance = findDistances(sm); + // System.err.println("Made distances");// dbg makeLeaves(); -// System.err.println("Made leaves");// dbg - + // System.err.println("Made leaves");// dbg + noClus = cluster.size(); cluster(); -// System.err.println("Made clusters");// dbg - + // System.err.println("Made clusters");// dbg + } /** - * DOCUMENT ME! + * Generate a string representation of the Tree * - * @return DOCUMENT ME! + * @return Newick File with all tree data available */ public String toString() { jalview.io.NewickFile fout = new jalview.io.NewickFile(getTopNode()); - return fout.print(false, true); // distances only + return fout.print(isHasBootstrap(), isHasDistances(), + isHasRootDistance()); // output all data available for tree } /** * * used when the alignment associated to a tree has changed. * - * @param alignment - * Vector + * @param list + * Sequence set to be associated with tree nodes */ - public void UpdatePlaceHolders(Vector alignment) + public void UpdatePlaceHolders(List list) { Vector leaves = new Vector(); findLeaves(top, leaves); @@ -299,7 +310,7 @@ public class NJTree { SequenceNode leaf = (SequenceNode) leaves.elementAt(i++); - if (alignment.contains(leaf.element())) + if (list.contains(leaf.element())) { leaf.setPlaceholder(false); } @@ -308,11 +319,11 @@ public class NJTree if (seqmatcher == null) { // Only create this the first time we need it - SequenceI[] seqs = new SequenceI[alignment.size()]; + SequenceI[] seqs = new SequenceI[list.size()]; for (int j = 0; j < seqs.length; j++) { - seqs[j] = (SequenceI) alignment.elementAt(j); + seqs[j] = list.get(j); } seqmatcher = new SequenceIdMatcher(seqs); @@ -348,6 +359,28 @@ public class NJTree } /** + * rename any nodes according to their associated sequence. This will modify + * the tree's metadata! (ie the original NewickFile or newly generated + * BinaryTree's label data) + */ + public void renameAssociatedNodes() + { + applyToNodes(new NodeTransformI() + { + + @Override + public void transform(BinaryNode node) + { + Object el = node.element(); + if (el != null && el instanceof SequenceI) + { + node.setName(((SequenceI) el).getName()); + } + } + }); + } + + /** * DOCUMENT ME! */ public void cluster() @@ -406,9 +439,9 @@ public class NJTree * DOCUMENT ME! * * @param i - * DOCUMENT ME! + * DOCUMENT ME! * @param j - * DOCUMENT ME! + * DOCUMENT ME! * * @return DOCUMENT ME! */ @@ -474,11 +507,11 @@ public class NJTree * DOCUMENT ME! * * @param tmpi - * DOCUMENT ME! + * DOCUMENT ME! * @param tmpj - * DOCUMENT ME! + * DOCUMENT ME! * @param dist - * DOCUMENT ME! + * DOCUMENT ME! */ public void findNewNJDistances(SequenceNode tmpi, SequenceNode tmpj, float dist) @@ -502,11 +535,11 @@ public class NJTree * DOCUMENT ME! * * @param tmpi - * DOCUMENT ME! + * DOCUMENT ME! * @param tmpj - * DOCUMENT ME! + * DOCUMENT ME! * @param dist - * DOCUMENT ME! + * DOCUMENT ME! */ public void findNewDistances(SequenceNode tmpi, SequenceNode tmpj, float dist) @@ -537,9 +570,9 @@ public class NJTree * DOCUMENT ME! * * @param i - * DOCUMENT ME! + * DOCUMENT ME! * @param j - * DOCUMENT ME! + * DOCUMENT ME! */ public void findClusterDistance(int i, int j) { @@ -573,9 +606,9 @@ public class NJTree * DOCUMENT ME! * * @param i - * DOCUMENT ME! + * DOCUMENT ME! * @param j - * DOCUMENT ME! + * DOCUMENT ME! */ public void findClusterNJDistance(int i, int j) { @@ -606,9 +639,9 @@ public class NJTree * DOCUMENT ME! * * @param i - * DOCUMENT ME! + * DOCUMENT ME! * @param j - * DOCUMENT ME! + * DOCUMENT ME! * * @return DOCUMENT ME! */ @@ -693,98 +726,26 @@ public class NJTree } /** - * DOCUMENT ME! + * Calculate a distance matrix given the sequence input data and score model * - * @return DOCUMENT ME! + * @return similarity matrix used to compute tree */ - public float[][] findDistances(String[] sequenceString) + public float[][] findDistances(ScoreModelI _pwmatrix) { - float[][] distance = new float[noseqs][noseqs]; - - if (pwtype.equals("PID")) - { - for (int i = 0; i < (noseqs - 1); i++) - { - for (int j = i; j < noseqs; j++) - { - if (j == i) - { - distance[i][i] = 0; - } - else - { - distance[i][j] = 100 - Comparison.PID(sequenceString[i], - sequenceString[j]); - distance[j][i] = distance[i][j]; - } - } - } - } - else + float[][] distance = new float[noseqs][noseqs]; + if (_pwmatrix == null) { - // Pairwise substitution score (with no gap penalties) - ScoreMatrix pwmatrix = ResidueProperties.getScoreMatrix(pwtype); - if (pwmatrix == null) - { - pwmatrix = ResidueProperties.getScoreMatrix("BLOSUM62"); - } - int maxscore = 0; - int end = sequenceString[0].length(); - for (int i = 0; i < (noseqs - 1); i++) - { - for (int j = i; j < noseqs; j++) - { - int score = 0; - - for (int k = 0; k < end; k++) - { - try - { - score += pwmatrix.getPairwiseScore(sequenceString[i] - .charAt(k), sequenceString[j].charAt(k)); - } catch (Exception ex) - { - System.err.println("err creating BLOSUM62 tree"); - ex.printStackTrace(); - } - } - - distance[i][j] = (float) score; - - if (score > maxscore) - { - maxscore = score; - } - } - } - - for (int i = 0; i < (noseqs - 1); i++) + // Resolve substitution model + _pwmatrix = ResidueProperties.getScoreModel(pwtype); + if (_pwmatrix == null) { - for (int j = i; j < noseqs; j++) - { - distance[i][j] = (float) maxscore - distance[i][j]; - distance[j][i] = distance[i][j]; - } + _pwmatrix = ResidueProperties.getScoreMatrix("BLOSUM62"); } - } + distance = _pwmatrix.findDistances(seqData); return distance; - // else - /* - * else if (pwtype.equals("SW")) { float max = -1; - * - * for (int i = 0; i < (noseqs - 1); i++) { for (int j = i; j < noseqs; j++) { - * AlignSeq as = new AlignSeq(sequence[i], sequence[j], "pep"); - * as.calcScoreMatrix(); as.traceAlignment(); as.printAlignment(System.out); - * distance[i][j] = (float) as.maxscore; - * - * if (max < distance[i][j]) { max = distance[i][j]; } } } - * - * for (int i = 0; i < (noseqs - 1); i++) { for (int j = i; j < noseqs; j++) { - * distance[i][j] = max - distance[i][j]; distance[j][i] = distance[i][j]; } } }/ - */ } /** @@ -814,9 +775,9 @@ public class NJTree * Search for leaf nodes. * * @param node - * root node to search from + * root node to search from * @param leaves - * Vector of leaves to add leaf node objects too. + * Vector of leaves to add leaf node objects too. * * @return Vector of leaf nodes on binary tree */ @@ -828,7 +789,7 @@ public class NJTree } if ((node.left() == null) && (node.right() == null)) // Interior node - // detection + // detection { leaves.addElement(node); @@ -851,9 +812,9 @@ public class NJTree * Find the leaf node with a particular ycount * * @param node - * initial point on tree to search from + * initial point on tree to search from * @param count - * value to search for + * value to search for * * @return null or the node with ycound=count */ @@ -866,7 +827,6 @@ public class NJTree /* * #see findLeaf(SequenceNode node, count) - * */ public Object _findLeaf(SequenceNode node, int count) { @@ -894,7 +854,7 @@ public class NJTree * printNode is mainly for debugging purposes. * * @param node - * SequenceNode + * SequenceNode */ public void printNode(SequenceNode node) { @@ -907,12 +867,12 @@ public class NJTree { System.out .println("Leaf = " + ((SequenceI) node.element()).getName()); - System.out.println("Dist " + ((SequenceNode) node).dist); + System.out.println("Dist " + node.dist); System.out.println("Boot " + node.getBootstrap()); } else { - System.out.println("Dist " + ((SequenceNode) node).dist); + System.out.println("Dist " + node.dist); printNode((SequenceNode) node.left()); printNode((SequenceNode) node.right()); } @@ -922,7 +882,7 @@ public class NJTree * DOCUMENT ME! * * @param node - * DOCUMENT ME! + * DOCUMENT ME! */ public void findMaxDist(SequenceNode node) { @@ -933,11 +893,11 @@ public class NJTree if ((node.left() == null) && (node.right() == null)) { - float dist = ((SequenceNode) node).dist; + float dist = node.dist; if (dist > maxDistValue) { - maxdist = (SequenceNode) node; + maxdist = node; maxDistValue = dist; } } @@ -972,9 +932,9 @@ public class NJTree * DOCUMENT ME! * * @param node - * DOCUMENT ME! + * DOCUMENT ME! * @param threshold - * DOCUMENT ME! + * DOCUMENT ME! */ public void groupNodes(SequenceNode node, float threshold) { @@ -998,7 +958,7 @@ public class NJTree * DOCUMENT ME! * * @param node - * DOCUMENT ME! + * DOCUMENT ME! * * @return DOCUMENT ME! */ @@ -1119,7 +1079,7 @@ public class NJTree * DOCUMENT ME! * * @param node - * DOCUMENT ME! + * DOCUMENT ME! */ public void printN(SequenceNode node) { @@ -1139,37 +1099,38 @@ public class NJTree + ((SequenceI) node.element()).getName()); } - System.out.println(" dist = " + ((SequenceNode) node).dist + " " - + ((SequenceNode) node).count + " " - + ((SequenceNode) node).height); + System.out.println(" dist = " + node.dist + " " + node.count + " " + + node.height); } /** * DOCUMENT ME! * * @param node - * DOCUMENT ME! + * DOCUMENT ME! */ public void reCount(SequenceNode node) { ycount = 0; - _lycount=0; -// _lylimit = this.node.size(); + _lycount = 0; + // _lylimit = this.node.size(); _reCount(node); } - private long _lycount=0,_lylimit=0; + + private long _lycount = 0, _lylimit = 0; + /** * DOCUMENT ME! * * @param node - * DOCUMENT ME! + * DOCUMENT ME! */ public void _reCount(SequenceNode node) { -// if (_lycount<_lylimit) -// { -// System.err.println("Warning: depth of _recount greater than number of nodes."); -// } + // if (_lycount<_lylimit) + // { + // System.err.println("Warning: depth of _recount greater than number of nodes."); + // } if (node == null) { return; @@ -1178,20 +1139,20 @@ public class NJTree if ((node.left() != null) && (node.right() != null)) { - + _reCount((SequenceNode) node.left()); _reCount((SequenceNode) node.right()); SequenceNode l = (SequenceNode) node.left(); SequenceNode r = (SequenceNode) node.right(); - ((SequenceNode) node).count = l.count + r.count; - ((SequenceNode) node).ycount = (l.ycount + r.ycount) / 2; + node.count = l.count + r.count; + node.ycount = (l.ycount + r.ycount) / 2; } else { - ((SequenceNode) node).count = 1; - ((SequenceNode) node).ycount = ycount++; + node.count = 1; + node.ycount = ycount++; } _lycount--; } @@ -1200,7 +1161,7 @@ public class NJTree * DOCUMENT ME! * * @param node - * DOCUMENT ME! + * DOCUMENT ME! */ public void swapNodes(SequenceNode node) { @@ -1219,9 +1180,9 @@ public class NJTree * DOCUMENT ME! * * @param node - * DOCUMENT ME! + * DOCUMENT ME! * @param dir - * DOCUMENT ME! + * DOCUMENT ME! */ public void changeDirection(SequenceNode node, SequenceNode dir) { @@ -1320,15 +1281,19 @@ public class NJTree { return hasRootDistance; } + /** * apply the given transform to all the nodes in the tree. + * * @param nodeTransformI */ public void applyToNodes(NodeTransformI nodeTransformI) { - for (Enumeration nodes = node.elements(); nodes.hasMoreElements(); - nodeTransformI.transform((BinaryNode)nodes.nextElement())) + for (Enumeration nodes = node.elements(); nodes.hasMoreElements(); nodeTransformI + .transform((BinaryNode) nodes.nextElement())) + { ; + } } } @@ -1346,7 +1311,7 @@ class Cluster * Creates a new Cluster object. * * @param value - * DOCUMENT ME! + * DOCUMENT ME! */ public Cluster(int[] value) {