001/* 002 * PDB web development code 003 * 004 * This code may be freely distributed and modified under the 005 * terms of the GNU Lesser General Public Licence. This should 006 * be distributed with the code. If you do not have a copy, 007 * see: 008 * 009 * http://www.gnu.org/copyleft/lesser.html 010 * 011 * Copyright for this code is held jointly by the individual 012 * authors. These should be listed in @author doc comments. 013 * 014 * 015 * Created on Jun 17, 2009 016 * Created by ap3 017 * 018 */ 019package org.biojava.nbio.structure.align.model; 020 021import org.biojava.nbio.structure.Atom; 022import org.biojava.nbio.structure.align.ce.CeMain; 023import org.biojava.nbio.structure.align.ce.CeSideChainMain; 024import org.biojava.nbio.structure.align.util.AFPAlignmentDisplay; 025import org.biojava.nbio.structure.jama.Matrix; 026 027import java.io.Serializable; 028import java.util.ArrayList; 029import java.util.Arrays; 030import java.util.List; 031import java.util.Map; 032 033/** 034 * A bean to contain the core of a structure alignment. 035 * The FatCat aligner class is working on the AFPChain class. 036 * 037 * @author Andreas Prlic 038 * @author Aleix Lafita 039 * 040 */ 041public class AFPChain implements Serializable, Cloneable { 042 043 private static final long serialVersionUID = -4474029015606617947L; 044 public static final String newline = System.getProperty("line.separator"); 045 public static final String UNKNOWN_ALGORITHM = "unknown"; 046 047 private String algorithmName; 048 private String version; 049 050 private String name1; 051 private String name2; 052 private long ioTime; 053 private long calculationTime; 054 private long id; 055 056 // results: 057 private double alignScore; 058 private double alignScoreUpdate; 059 private int afpChainTwiNum; 060 061 // end of results 062 private double tmScore; 063 064 // utility 065 private int minLen ; // the length of the shorter 2 proteins. 066 067 068 private List<AFP> afpSet; 069 private int[][] afpIndex; 070 private int[][] afpAftIndex; 071 private int[][] afpBefIndex; 072 073 private Matrix disTable1; 074 private Matrix disTable2; 075 076 private int[] twi = null ; //the number of twists making the best score ending at each AFP 077 078 private int afpChainLen; 079 private int[] afpChainList; 080 private double[] afpChainTwiBin; 081 private double[] afpChainTwiList; 082 private double chainRmsd; 083 084 private int chainLen,misLen,gapLen; 085 private int blockNum; //the final block number 086 private int blockNumIni; //block number before block clustering and split 087 private int blockNumClu; //block number after clustering blocks 088 private int blockNumSpt; //block number after spliting blocks 089 private double[] blockRmsd; //the RMSD of each block 090 private int[] block2Afp; //the index of afp for each block 091 private int[] blockSize; //the number of AFPs involved in a block 092 private double[] blockScore; //the score associated with each block 093 private int[] blockGap; //the gaps in each block 094 private int[] blockResSize; //the number of residues involved in a block 095 private int[][][] blockResList;//the list of AFP for each block 096 private Matrix[] blockRotationMatrix; 097 private Atom[] blockShiftVector; 098 099 private int focusResn; //the size of the set 100 private int[] focusRes1; //the residues from protein 1 101 private int[] focusRes2; //the residues from protein 2 102 private int focusAfpn; //the AFP number 103 private int[] focusAfpList; //the AFP list 104 105 private boolean shortAlign; 106 107 private String [][][] pdbAln; // only needed temp. during XML serialization, since we don;t have coordinates loaded at that time and can map from PDB res numbers to atom positions. 108 private int[][][] optAln; 109 private int[] optLen ; 110 private double[] optRmsd ; 111 private int optLength; 112 113 private char[] alnsymb; 114 private char[] alnseq1; 115 private char[] alnseq2; 116 private int alnLength; 117 private int alnbeg1; 118 private int alnbeg2; 119 120 private int totalLenIni; 121 private int totalLenOpt = 0; 122 123 private double totalRmsdIni; 124 private double totalRmsdOpt; 125 126 private int ca1Length; 127 private int ca2Length; 128 129 // this one is special. it comes from the FatCatParameters... 130 // default is flexible alignment... 131 private int maxTra = 5; 132 133 private Double conn; 134 private Double dvar; 135 136 private double probability; 137 private double identity; 138 private double similarity; 139 private double normAlignScore; 140 141 private int myResultsEQR; 142 private int myResultsSimilarity1; 143 private int myResultsSimilarity2; 144 145 // Mark whether the alignment topology is sequential 146 // false if a circular permutation has occured 147 private boolean sequentialAlignment; 148 149 // background distances 150 private Matrix distanceMatrix; 151 152 private String description2; 153 154 /** 155 * Construction of an AFPChain needs the algorithm name, since downstream 156 * analysis methods (scores, display, etc) behave differently if the 157 * alignment is flexible (created with FatCat). 158 * 159 * @param algorithmName 160 */ 161 public AFPChain(String algorithmName){ 162 this.algorithmName = algorithmName; 163 init(); 164 } 165 166 /** 167 * Use the constructor with the algorithmName (design condition). 168 * @see AFPChain#AFPChain(String) 169 */ 170 @Deprecated 171 public AFPChain(){ 172 algorithmName = UNKNOWN_ALGORITHM; 173 init(); 174 } 175 176 /** 177 * Copy constructor 178 * @param o AFPChain to duplicate 179 */ 180 public AFPChain(AFPChain o) { 181 this.algorithmName = o.algorithmName; 182 this.version = o.version; 183 this.name1 = o.name1; 184 this.name2 = o.name2; 185 this.ioTime = o.ioTime; 186 this.calculationTime = o.calculationTime; 187 this.id = o.id; 188 this.alignScore = o.alignScore; 189 this.alignScoreUpdate = o.alignScoreUpdate; 190 this.afpChainTwiNum = o.afpChainTwiNum; 191 this.minLen = o.minLen; 192 this.afpSet = new ArrayList<AFP>(o.afpSet); 193 this.afpIndex = o.afpIndex == null? null: o.afpIndex.clone(); 194 this.afpAftIndex = o.afpAftIndex == null? null: o.afpAftIndex.clone(); 195 this.afpBefIndex = o.afpBefIndex == null? null: o.afpBefIndex.clone(); 196 this.disTable1 = o.disTable1 == null? null: (Matrix) o.disTable1.clone(); 197 this.disTable2 = o.disTable2 == null? null: (Matrix) o.disTable2.clone(); 198 this.twi = o.twi == null ? null : o.twi.clone(); 199 this.afpChainLen = o.afpChainLen; 200 this.afpChainList = o.afpChainList == null? null: o.afpChainList.clone(); 201 this.afpChainTwiBin = o.afpChainTwiBin == null? null: o.afpChainTwiBin.clone(); 202 this.afpChainTwiList = o.afpChainTwiList == null? null: o.afpChainTwiList.clone(); 203 this.chainRmsd = o.chainRmsd; 204 this.chainLen = o.chainLen; 205 this.misLen = o.misLen; 206 this.gapLen = o.gapLen; 207 this.blockNum = o.blockNum; 208 this.blockNumIni = o.blockNumIni; 209 this.blockNumClu = o.blockNumClu; 210 this.blockNumSpt = o.blockNumSpt; 211 this.blockRmsd = o.blockRmsd == null ? null : o.blockRmsd.clone(); 212 this.block2Afp = o.block2Afp == null ? null : o.block2Afp.clone(); 213 this.blockSize = o.blockSize == null ? null : o.blockSize.clone(); 214 this.blockScore = o.blockScore == null ? null : o.blockScore.clone(); 215 this.blockGap = o.blockGap == null ? null : o.blockGap.clone(); 216 this.blockResSize = o.blockResSize == null ? null : o.blockResSize.clone(); 217 this.blockResList = o.blockResList == null ? null : o.blockResList.clone(); 218 this.blockRotationMatrix = o.blockRotationMatrix == null ? null : o.blockRotationMatrix.clone(); 219 this.blockShiftVector = o.blockShiftVector == null ? null : o.blockShiftVector.clone(); 220 this.focusResn = o.focusResn; 221 this.focusRes1 = o.focusRes1 == null ? null : o.focusRes1.clone(); 222 this.focusRes2 = o.focusRes2 == null ? null : o.focusRes2.clone(); 223 this.focusAfpn = o.focusAfpn; 224 this.focusAfpList = o.focusAfpList == null ? null : o.focusAfpList.clone(); 225 this.shortAlign = o.shortAlign; 226 this.pdbAln = o.pdbAln == null ? null : o.pdbAln.clone(); 227 this.optAln = o.optAln == null ? null : o.optAln.clone(); 228 this.optLen = o.optLen == null ? null : o.optLen.clone(); 229 this.optRmsd = o.optRmsd == null ? null : o.optRmsd.clone(); 230 this.optLength = o.optLength; 231 this.alnsymb = o.alnsymb == null ? null : o.alnsymb.clone(); 232 this.alnseq1 = o.alnseq1 == null ? null : o.alnseq1.clone(); 233 this.alnseq2 = o.alnseq2 == null ? null : o.alnseq2.clone(); 234 this.alnLength = o.alnLength; 235 this.alnbeg1 = o.alnbeg1; 236 this.alnbeg2 = o.alnbeg2; 237 this.totalLenIni = o.totalLenIni; 238 this.totalLenOpt = o.totalLenOpt; 239 this.totalRmsdIni = o.totalRmsdIni; 240 this.totalRmsdOpt = o.totalRmsdOpt; 241 this.ca1Length = o.ca1Length; 242 this.ca2Length = o.ca2Length; 243 this.maxTra = o.maxTra; 244 this.conn = new Double(o.conn); 245 this.dvar = new Double(o.dvar); 246 this.probability = o.probability; 247 this.identity = o.identity; 248 this.similarity = o.similarity; 249 this.normAlignScore = o.normAlignScore; 250 this.myResultsEQR = o.myResultsEQR; 251 this.myResultsSimilarity1 = o.myResultsSimilarity1; 252 this.myResultsSimilarity2 = o.myResultsSimilarity2; 253 this.distanceMatrix = o.distanceMatrix; 254 } 255 256 /** 257 * Creates and returns a copy of this object. 258 */ 259 @Override 260 public Object clone() { 261 return new AFPChain(this); 262 } 263 264 public long getId() 265 { 266 return id; 267 } 268 public void setId(long id) 269 { 270 this.id = id; 271 } 272 273 public String toCE(Atom[] ca1, Atom[]ca2) { 274 275 return AfpChainWriter.toCE(this,ca1,ca2); 276 277 } 278 279 public String toRotMat(){ 280 281 return AfpChainWriter.toRotMat(this); 282 } 283 284 public String toFatcat(Atom[] ca1, Atom[]ca2){ 285 286 return AfpChainWriter.toFatCat(this,ca1,ca2); 287 288 } 289 290 public String toDBSearchResult(){ 291 292 return AfpChainWriter.toDBSearchResult(this); 293 } 294 295 protected void calcSimilarity() { 296 Map<String,Double> idMap = AFPAlignmentDisplay.calcIdSimilarity(alnseq1,alnseq2,alnLength); 297 298 //probability = idMap.get("probability"); 299 similarity = idMap.get("similarity"); 300 identity = idMap.get("identity"); 301 302 } 303 304 305 306 307 /** 308 * Get the number of structurally equivalent residues 309 * 310 * @return nr of EQR 311 */ 312 public int getNrEQR(){ 313 314 if (myResultsEQR < 0){ 315 if ( optLen == null) { 316 myResultsEQR = 0; 317 return 0; 318 } 319 320 int nrEqr = 0; 321 for(int bk = 0; bk < blockNum; bk ++) { 322 323 for ( int i=0;i< optLen[bk];i++){ 324 nrEqr++; 325 } 326 } 327 myResultsEQR = nrEqr; 328 } 329 return myResultsEQR; 330 } 331 332 /** Get the coverage of protein 1 with the alignment 333 * 334 * @return percentage of coverage, between 0 and 100. 335 */ 336 public int getCoverage1(){ 337 if ( myResultsSimilarity1 < 0 ) { 338 int distance = ca1Length + ca2Length - 2 * getNrEQR(); 339 340 int similarity = (ca1Length + ca2Length - distance ) / 2; 341 342 myResultsSimilarity1 = Math.round(similarity /(float) ca1Length * 100); 343 } 344 return myResultsSimilarity1; 345 } 346 347 /** Get the coverage of protein 2 with the alignment 348 * 349 * @return percentage of coverage, between 0 and 100. 350 */ 351 public int getCoverage2(){ 352 if ( myResultsSimilarity2 < 0 ) { 353 354 355 int distance = ca1Length + ca2Length - 2 * getNrEQR(); 356 357 int similarity = (ca1Length + ca2Length - distance ) / 2; 358 myResultsSimilarity2 = Math.round(similarity /(float) ca2Length * 100); 359 } 360 return myResultsSimilarity2; 361 362 } 363 364 /** get the coverage of protein 1 with the alignment 365 * 366 * @return percentage of coverage, between 0 and 100. 367 * @deprecated use getCoverage1() instead 368 */ 369 @Deprecated 370 public int getSimilarity1(){ 371 return getCoverage1(); 372 373 } 374 375 /** get the coverage of protein 2 with the alignment 376 * 377 * @return percentage of coverage, between 0 and 100. 378 * @deprecated use getCoverage2() instead 379 */ 380 @Deprecated 381 public int getSimilarity2(){ 382 return getCoverage2(); 383 384 } 385 386 @Override 387 public String toString(){ 388 389 //int lA = ca1Length; 390 //int lB = ca2Length; 391 //int distance = lA + lB - 2 * getNrEQR(); 392 393 StringBuffer str = new StringBuffer(""); 394 str.append("EQR:"); 395 str.append(getNrEQR()); 396 397 str.append("\tLen1:"); 398 str.append(this.getCa1Length()); 399 str.append("\tLen2:"); 400 str.append(this.getCa2Length()); 401 str.append(String.format("\tscore: %.2f",this.getAlignScore())); 402 str.append("\t"); 403 if ( algorithmName.equalsIgnoreCase(CeMain.algorithmName) || algorithmName.equalsIgnoreCase(CeSideChainMain.algorithmName)){ 404 str.append("Z-score:"); 405 str.append(String.format("%.2f",this.getProbability())); 406 } else { 407 str.append("Probability:"); 408 str.append(String.format("%.2e",this.getProbability())); 409 } 410 str.append("\tRMSD:"); 411 str.append(String.format("%.2f",this.getTotalRmsdOpt())); 412 413 str.append("\tSeqID:"); 414 str.append(String.format("%.0f",getIdentity()*100)); 415 str.append("%\tSeqSim:"); 416 str.append(String.format("%.0f",getSimilarity()*100)); 417 str.append("%\tCov1:"); 418 str.append(this.getCoverage1()); 419 str.append("%\tCov2:"); 420 str.append(this.getCoverage2()); 421 str.append("%"); 422 423 if ( tmScore != -1) { 424 str.append("\ttmScore:"); 425 str.append(String.format("%.2f",tmScore)); 426 } 427 str.append(newline); 428 429 430 return str.toString(); 431 } 432 433 public boolean isSignificantResult(){ 434 if ( algorithmName.equalsIgnoreCase(CeMain.algorithmName) || algorithmName.equalsIgnoreCase(CeSideChainMain.algorithmName)){ 435 if (probability >= 3.5) 436 return true; 437 } else { 438 if (probability < 0.01) 439 return true; 440 } 441 return false; 442 } 443 444 445 446 447 private void init(){ 448 shortAlign = false; 449 afpChainLen = 0; 450 451 afpChainList = null; 452 afpChainTwiBin = null; 453 afpChainTwiList = null; 454 chainRmsd=0; 455 chainLen = misLen = gapLen = 0; 456 457 blockResSize = null; 458 blockScore = null; 459 blockGap = null; 460 optAln = null; 461 pdbAln = null; 462 optLen = null; 463 464 optRmsd = null; 465 466 block2Afp = new int[maxTra+1]; 467 blockSize = new int[maxTra+1]; 468 blockRmsd = new double[maxTra+1]; 469 blockScore = new double[maxTra+1]; 470 blockGap = new int[maxTra+1]; 471 472 blockResSize = new int[maxTra+1]; 473 474 afpSet = new ArrayList<AFP>(); 475 totalLenIni = totalLenOpt = 0; 476 totalRmsdIni = totalRmsdOpt = 0.0; 477 478 afpChainTwiNum = 0; 479 alignScore = 0; 480 alignScoreUpdate = 0; 481 conn = new Double(0); 482 dvar = new Double(0); 483 calculationTime = 0; 484 485 similarity = -1; 486 identity = -1; 487 myResultsEQR = -1; 488 myResultsSimilarity1 = -1; 489 myResultsSimilarity2 = -1; 490 version = "1.0"; 491 sequentialAlignment = true; 492 distanceMatrix = null; 493 tmScore = -1; 494 description2=null; 495 } 496 497 /** 498 * Resets properties which can be calculated on the fly 499 */ 500 private void invalidate() { 501 myResultsEQR = -1; 502 myResultsSimilarity1 = -1; 503 myResultsSimilarity2 = -1; 504 identity = -1; 505 similarity = -1; 506 } 507 508 /** used temporarily during XML serialization to track the PDB positions of the alignmnet 509 * 510 * @return String array 511 */ 512 public String[][][] getPdbAln() { 513 return pdbAln; 514 } 515 516 517 public void setPdbAln(String[][][] pdbAln) { 518 this.pdbAln = pdbAln; 519 } 520 521 522 public Double getConn() 523 { 524 return conn; 525 } 526 527 528 public void setConn(Double conn) 529 { 530 this.conn = conn; 531 } 532 533 534 public Double getDVar() 535 { 536 return dvar; 537 } 538 539 540 public void setDVar(Double dvar) 541 { 542 this.dvar = dvar; 543 } 544 545 546 /** get the maximum nr of Twists that are allowed... 547 * 548 * @return maxTra, the max nr of twists 549 */ 550 public int getMaxTra() 551 { 552 return maxTra; 553 } 554 555 /** 556 * Set the maximum number of Twists that are allowed... 557 * @param maxTra 558 */ 559 public void setMaxTra(int maxTra) 560 { 561 this.maxTra = maxTra; 562 } 563 564 565 public double getAlignScore() 566 { 567 return alignScore; 568 } 569 570 public void setAlignScore(double alignScore) 571 { 572 this.alignScore = alignScore; 573 } 574 575 public double getAlignScoreUpdate() 576 { 577 return alignScoreUpdate; 578 } 579 580 public void setAlignScoreUpdate(double alignScoreUpdate) 581 { 582 this.alignScoreUpdate = alignScoreUpdate; 583 } 584 585 public int getAfpChainTwiNum() 586 { 587 return afpChainTwiNum; 588 } 589 590 public void setAfpChainTwiNum(int afpChainTwiNum) 591 { 592 this.afpChainTwiNum = afpChainTwiNum; 593 } 594 595 public int getMinLen() 596 { 597 return minLen; 598 } 599 600 public void setMinLen(int minLen) 601 { 602 this.minLen = minLen; 603 } 604 605 606 607 /** 608 * Get the set of AFPs for this alignment. 609 * An AFP is a local ungapped alignment between the two peptides. 610 * 611 * AFPs are set before the final optimization step. To get the final 612 * alignment, look at the aligned pairs from {@link #getOptAln()}. 613 * 614 * @return The optimal set of AFPs 615 * @see #getOptAln() 616 */ 617 public List<AFP> getAfpSet() 618 { 619 return afpSet; 620 } 621 622 623 /** 624 * Set the set of AFPs for this alignment. 625 * An AFP is a local ungapped alignment between the two peptides. 626 * 627 * AFPs are set before the final optimization step. To get the final 628 * alignment, look at the aligned pairs from {@link #getOptAln()}. 629 */ 630 public void setAfpSet(List<AFP> afpSet) 631 { 632 this.afpSet = afpSet; 633 } 634 635 public int[][] getAfpIndex() 636 { 637 return afpIndex; 638 } 639 640 public void setAfpIndex(int[][] afpIndex) 641 { 642 this.afpIndex = afpIndex; 643 } 644 645 646 public int[][] getAfpAftIndex() 647 { 648 return afpAftIndex; 649 } 650 651 public void setAfpAftIndex(int[][] afpAftIndex) 652 { 653 this.afpAftIndex = afpAftIndex; 654 } 655 656 657 public int[][] getAfpBefIndex() 658 { 659 return afpBefIndex; 660 } 661 662 public void setAfpBefIndex(int[][] afpBefIndex) 663 { 664 this.afpBefIndex = afpBefIndex; 665 } 666 667 668 public Matrix getDisTable1() 669 { 670 return disTable1; 671 } 672 673 public void setDisTable1(Matrix disTable1) 674 { 675 this.disTable1 = disTable1; 676 } 677 678 679 public Matrix getDisTable2() 680 { 681 return disTable2; 682 } 683 684 public void setDisTable2(Matrix disTable2) 685 { 686 this.disTable2 = disTable2; 687 } 688 689 690 public int[] getTwi() 691 { 692 return twi; 693 } 694 695 public void setTwi(int[] twi) 696 { 697 this.twi = twi; 698 } 699 700 public int getAfpChainLen() 701 { 702 return afpChainLen; 703 } 704 705 public void setAfpChainLen(int afpChainLen) 706 { 707 this.afpChainLen = afpChainLen; 708 } 709 710 public int[] getAfpChainList() 711 { 712 return afpChainList; 713 } 714 715 public void setAfpChainList(int[] afpChainList) 716 { 717 this.afpChainList = afpChainList; 718 } 719 720 public double[] getAfpChainTwiBin() 721 { 722 return afpChainTwiBin; 723 } 724 725 public void setAfpChainTwiBin(double[] afpChainTwiBin) 726 { 727 this.afpChainTwiBin = afpChainTwiBin; 728 } 729 730 public double[] getAfpChainTwiList() 731 { 732 return afpChainTwiList; 733 } 734 735 public void setAfpChainTwiList(double[] afpChainTwiList) 736 { 737 this.afpChainTwiList = afpChainTwiList; 738 } 739 740 public double getChainRmsd() 741 { 742 return chainRmsd; 743 } 744 745 /** The RMSD of the chain of AFPs. Set during AFPCHainer.traceBack(); 746 * 747 * @param chainRmsd 748 */ 749 public void setChainRmsd(double chainRmsd) 750 { 751 this.chainRmsd = chainRmsd; 752 } 753 754 public int getChainLen() 755 { 756 return chainLen; 757 } 758 759 public void setChainLen(int chainLen) 760 { 761 this.chainLen = chainLen; 762 } 763 764 public int getMisLen() 765 { 766 return misLen; 767 } 768 769 public void setMisLen(int misLen) 770 { 771 this.misLen = misLen; 772 } 773 774 public int getGapLen() 775 { 776 return gapLen; 777 } 778 779 public void setGapLen(int gapLen) 780 { 781 this.gapLen = gapLen; 782 } 783 784 /** The number of blocks in the alignment 785 * 786 * @return the nr of blocks in alignment 787 */ 788 public int getBlockNum() 789 { 790 return blockNum; 791 } 792 793 public void setBlockNum(int blockNum) 794 { 795 this.blockNum = blockNum; 796 } 797 798 public int getBlockNumIni() 799 { 800 return blockNumIni; 801 } 802 803 public void setBlockNumIni(int blockNumIni) 804 { 805 this.blockNumIni = blockNumIni; 806 } 807 808 public int getBlockNumClu() 809 { 810 return blockNumClu; 811 } 812 813 public void setBlockNumClu(int blockNumClu) 814 { 815 this.blockNumClu = blockNumClu; 816 } 817 818 public int getBlockNumSpt() 819 { 820 return blockNumSpt; 821 } 822 823 public void setBlockNumSpt(int blockNumSpt) 824 { 825 this.blockNumSpt = blockNumSpt; 826 } 827 828 public double[] getBlockRmsd() 829 { 830 return blockRmsd; 831 } 832 833 public void setBlockRmsd(double[] blockRmsd) 834 { 835 this.blockRmsd = blockRmsd; 836 } 837 838 public int[] getBlock2Afp() 839 { 840 return block2Afp; 841 } 842 843 public void setBlock2Afp(int[] block2Afp) 844 { 845 this.block2Afp = block2Afp; 846 } 847 848 public int[] getBlockSize() 849 { 850 return blockSize; 851 } 852 853 public void setBlockSize(int[] blockSize) 854 { 855 this.blockSize = blockSize; 856 } 857 858 public double[] getBlockScore() 859 { 860 return blockScore; 861 } 862 863 public void setBlockScore(double[] blockScore) 864 { 865 this.blockScore = blockScore; 866 } 867 868 public int[] getBlockGap() 869 { 870 return blockGap; 871 } 872 873 public void setBlockGap(int[] blockGap) 874 { 875 this.blockGap = blockGap; 876 } 877 878 public int[] getBlockResSize() 879 { 880 return blockResSize; 881 } 882 883 public void setBlockResSize(int[] blockResSize) 884 { 885 this.blockResSize = blockResSize; 886 } 887 888 889 /** tracks the residues of the initial blocks (before optimization) 890 * 891 * 892 * @return list of block residues 893 */ 894 public int[][][] getBlockResList() 895 { 896 return blockResList; 897 } 898 899 public void setBlockResList(int[][][] blockResList) 900 { 901 this.blockResList = blockResList; 902 } 903 904 public int getFocusResn() 905 { 906 return focusResn; 907 } 908 909 public void setFocusResn(int focusResn) 910 { 911 this.focusResn = focusResn; 912 } 913 914 915 public int[] getFocusRes1() 916 { 917 return focusRes1; 918 } 919 920 public void setFocusRes1(int[] focusRes1) 921 { 922 this.focusRes1 = focusRes1; 923 } 924 925 926 public int[] getFocusRes2() 927 { 928 return focusRes2; 929 } 930 931 public void setFocusRes2(int[] focusRes2) 932 { 933 this.focusRes2 = focusRes2; 934 } 935 936 public int getFocusAfpn() 937 { 938 return focusAfpn; 939 } 940 941 public void setFocusAfpn(int focusAfpn) 942 { 943 this.focusAfpn = focusAfpn; 944 } 945 946 public int[] getFocusAfpList() 947 { 948 return focusAfpList; 949 } 950 951 public void setFocusAfpList(int[] focusAfpList) 952 { 953 this.focusAfpList = focusAfpList; 954 } 955 956 public boolean isShortAlign() 957 { 958 return shortAlign; 959 } 960 961 public void setShortAlign(boolean shortAlign) 962 { 963 this.shortAlign = shortAlign; 964 } 965 966 /** Tracks the Atom positions in the optimal alignment. Note: only considers the equivalent positions, gaps are ignored... 967 * first dimension is the block nr 968 * second dimension is 0 or 1 (the alignment chain index) 969 * third is the position 970 * @return int array 971 */ 972 public int[][][] getOptAln() 973 { 974 return optAln; 975 } 976 977 public void setOptAln(int[][][] optAln) 978 { 979 invalidate(); 980 this.optAln = optAln; 981 } 982 983 /** 984 * The length of each block 985 * @return lengths 986 */ 987 public int[] getOptLen() 988 { 989 return optLen; 990 } 991 992 public void setOptLen(int[] optLen) 993 { 994 this.optLen = optLen; 995 } 996 997 public double[] getOptRmsd() 998 { 999 return optRmsd; 1000 } 1001 1002 public void setOptRmsd(double[] optRmsd) 1003 { 1004 this.optRmsd = optRmsd; 1005 } 1006 1007 public int getOptLength() 1008 { 1009 return optLength; 1010 } 1011 1012 /** The length of the optimal alignment. Set by AFPOptimizer.optimizeAln(). 1013 * This should be the sum of the elements in optLen 1014 * @param optLength 1015 */ 1016 public void setOptLength(int optLength) 1017 { 1018 this.optLength = optLength; 1019 } 1020 1021 1022 public char[] getAlnsymb() 1023 { 1024 return alnsymb; 1025 } 1026 1027 public void setAlnsymb(char[] alnsymb) 1028 { 1029 this.alnsymb = alnsymb; 1030 } 1031 1032 1033 public char[] getAlnseq1() 1034 { 1035 return alnseq1; 1036 } 1037 1038 public void setAlnseq1(char[] alnseq1) 1039 { 1040 this.alnseq1 = alnseq1; 1041 } 1042 1043 1044 public char[] getAlnseq2() 1045 { 1046 return alnseq2; 1047 } 1048 1049 public void setAlnseq2(char[] alnseq2) 1050 { 1051 this.alnseq2 = alnseq2; 1052 } 1053 1054 1055 /** 1056 * @return The total length of the alignment, including gaps 1057 * @see #getOptLength(), the number of aligned residues in the final alignment. 1058 */ 1059 public int getAlnLength() 1060 { 1061 return alnLength; 1062 } 1063 1064 public void setAlnLength(int alnLength) 1065 { 1066 this.alnLength = alnLength; 1067 } 1068 1069 /** 1070 * @return The index of the first aligned residue in protein 1 1071 */ 1072 public int getAlnbeg1() 1073 { 1074 return alnbeg1; 1075 } 1076 1077 public void setAlnbeg1(int alnbeg1) 1078 { 1079 this.alnbeg1 = alnbeg1; 1080 } 1081 /** 1082 * @return The index of the first aligned residue in protein 2 1083 */ 1084 public int getAlnbeg2() 1085 { 1086 return alnbeg2; 1087 } 1088 1089 public void setAlnbeg2(int alnbeg2) 1090 { 1091 this.alnbeg2 = alnbeg2; 1092 } 1093 1094 public int getTotalLenIni() 1095 { 1096 return totalLenIni; 1097 } 1098 1099 public void setTotalLenIni(int totalLenIni) 1100 { 1101 this.totalLenIni = totalLenIni; 1102 } 1103 1104 public int getTotalLenOpt() 1105 { 1106 return totalLenOpt; 1107 } 1108 1109 public void setTotalLenOpt(int totalLenOpt) 1110 { 1111 this.totalLenOpt = totalLenOpt; 1112 } 1113 1114 /** this is the init-RMSD, not the final RMSD after refinement. 1115 * 1116 * @return totalRmsdIni 1117 */ 1118 public double getTotalRmsdIni() 1119 { 1120 return totalRmsdIni; 1121 } 1122 1123 /** this is the init-RMSD, not the final RMSD after refinement. 1124 * 1125 * @param totalRmsdIni 1126 */ 1127 public void setTotalRmsdIni(double totalRmsdIni) 1128 { 1129 this.totalRmsdIni = totalRmsdIni; 1130 } 1131 1132 1133 /** The RMSD of the final alignment. Use this to print overal alignment RMSD. 1134 * 1135 * @return total RMSD of the optimal alignment. 1136 */ 1137 public double getTotalRmsdOpt() 1138 { 1139 return totalRmsdOpt; 1140 } 1141 1142 /** The RMSD of the final alignment. Use this to print overal alignment RMSD. 1143 * 1144 * @param totalRmsdOpt : total RMSD of the optimal alignment 1145 */ 1146 public void setTotalRmsdOpt(double totalRmsdOpt) 1147 { 1148 this.totalRmsdOpt = totalRmsdOpt; 1149 } 1150 1151 1152 public String getName1() 1153 { 1154 return name1; 1155 } 1156 1157 1158 public void setName1(String name1) 1159 { 1160 this.name1 = name1; 1161 } 1162 1163 1164 1165 public String getName2() 1166 { 1167 return name2; 1168 } 1169 1170 public void setName2(String name2) 1171 { 1172 this.name2 = name2; 1173 } 1174 1175 1176 public long getCalculationTime() 1177 { 1178 return calculationTime; 1179 } 1180 1181 public void setCalculationTime(long calculationTime) 1182 { 1183 this.calculationTime = calculationTime; 1184 } 1185 1186 public int getCa1Length() 1187 { 1188 return ca1Length; 1189 } 1190 1191 public void setCa1Length(int ca1Length) 1192 { 1193 this.ca1Length = ca1Length; 1194 } 1195 1196 public int getCa2Length() 1197 { 1198 return ca2Length; 1199 } 1200 1201 public void setCa2Length(int ca2Length) 1202 { 1203 this.ca2Length = ca2Length; 1204 } 1205 1206 public long getIoTime() 1207 { 1208 return ioTime; 1209 } 1210 1211 public void setIoTime(long ioTime) 1212 { 1213 this.ioTime = ioTime; 1214 } 1215 1216 /** The probability (FATCAT) or Z-score (CE) of the alignment. 1217 * 1218 * @return either the probability (FATCAT) or the Z-score (CE) of the alignment. 1219 */ 1220 public double getProbability() 1221 { 1222 return probability; 1223 } 1224 1225 public void setProbability(double probability) 1226 { 1227 this.probability = probability; 1228 } 1229 1230 /** The percent of residues that are sequence-identical in the alignment. 1231 * 1232 * @return a value between 0 and 1 1233 */ 1234 public double getIdentity() { 1235 if ( identity <= 0) { 1236 calcSimilarity(); 1237 } 1238 return identity; 1239 } 1240 1241 public void setIdentity(double identity) { 1242 1243 this.identity = identity; 1244 } 1245 1246 1247 /** Returns the similarity score for the alignment. This gives the percent of 1248 * sequence similar residues in the alignment. 1249 * 1250 * @return a double between 0 and 1 1251 */ 1252 public double getSimilarity() { 1253 if ( similarity < 0) 1254 calcSimilarity(); 1255 return similarity; 1256 } 1257 1258 public void setSimilarity(double similarity) { 1259 this.similarity = similarity; 1260 } 1261 1262 1263 public double getNormAlignScore() 1264 { 1265 return normAlignScore; 1266 } 1267 1268 public void setNormAlignScore(double normAlignScore) 1269 { 1270 this.normAlignScore = normAlignScore; 1271 } 1272 1273 public Matrix[] getBlockRotationMatrix() 1274 { 1275 return blockRotationMatrix; 1276 } 1277 1278 public void setBlockRotationMatrix(Matrix[] blockRotationMatrix) 1279 { 1280 this.blockRotationMatrix = blockRotationMatrix; 1281 } 1282 1283 public Atom[] getBlockShiftVector() 1284 { 1285 return blockShiftVector; 1286 } 1287 1288 public void setBlockShiftVector(Atom[] blockShiftVector) 1289 { 1290 this.blockShiftVector = blockShiftVector; 1291 } 1292 1293 public String getAlgorithmName() { 1294 return algorithmName; 1295 } 1296 1297 /** 1298 * Caution has to be made when changing the algorithmName of an AFPChain, 1299 * since downstream analysis methods (scores, display, etc) behave 1300 * differently if the alignment is flexible (created with FatCat). 1301 * 1302 * @param algorithmName 1303 */ 1304 public void setAlgorithmName(String algorithmName) { 1305 this.algorithmName = algorithmName; 1306 } 1307 1308 public String getVersion() { 1309 return version; 1310 } 1311 1312 public void setVersion(String version) { 1313 this.version = version; 1314 } 1315 1316 /** 1317 * Get whether this alignment has the normal topology, ie the residues 1318 * aligned in each block increase sequentially over the original protein. 1319 * 1320 * This will be false if a circular permutation was detected. 1321 * @return true if the alignment is sequential 1322 */ 1323 public boolean isSequentialAlignment() { 1324 return sequentialAlignment; 1325 } 1326 /** 1327 * Set whether this alignment has the normal topology, ie the residues 1328 * aligned in each block increase sequentially over the original protein. 1329 * 1330 * This will be false if a circular permutation was detected. 1331 */ 1332 public void setSequentialAlignment(boolean sequentialAlignment) { 1333 this.sequentialAlignment = sequentialAlignment; 1334 } 1335 1336 /** 1337 * A matrix with <i>ca1length</i> rows and <i>ca2length</i> columns. 1338 * For CE this is the distance matrix, but the exact interpretation is left 1339 * up to the alignment algorithm. 1340 * 1341 * <p>Note: 1342 * A {@link org.biojava.nbio.structure.gui.JMatrixPanel}, which is used in 1343 * the structure-gui package to display distance matrices, will display the 1344 * transpose of this matrix. Be sure to take that into account when debugging 1345 * visually. 1346 * 1347 * @return A matrix with dimensions ca1length x ca2length, or null 1348 */ 1349 public Matrix getDistanceMatrix() { 1350 return distanceMatrix; 1351 } 1352 1353 /** 1354 * A matrix with <i>ca1length</i> rows and <i>ca2length</i> columns. 1355 * For CE this is the distance matrix, but the exact interpretation is left 1356 * up to the alignment algorithm. 1357 * @param distanceMatrix A matrix with dimensions ca1length x ca2length 1358 */ 1359 public void setDistanceMatrix(Matrix distanceMatrix) { 1360 this.distanceMatrix = distanceMatrix; 1361 1362 //System.out.println("Setting distMatrix "+(distanceMatrix==null?"null":"not null")); 1363 } 1364 1365 1366 public void setTMScore(double tmScore){ 1367 this.tmScore = tmScore; 1368 } 1369 1370 /** Returns the tmScore of the alignment. If the score has not been calcualted yet, 1371 * returns -1. To calculate it call AFPChainScorer.getTMScore(afpChain, ca1, ca2); 1372 * 1373 * @return -1, if not calculated, or the TM-score, a score between 0 and 1 1374 */ 1375 public double getTMScore() 1376 { 1377 1378 return tmScore; 1379 } 1380 1381 1382 1383 /** Get a textual description for the protein 2 of the alignment. 1384 * 1385 * @return 1386 */ 1387 public String getDescription2() { 1388 return description2; 1389 } 1390 1391 1392 /** Set the textual description for protein 2. 1393 * 1394 * @param desc 1395 */ 1396 public void setDescription2(String desc){ 1397 this.description2 = desc; 1398 } 1399 1400 1401 /* (non-Javadoc) 1402 * @see java.lang.Object#hashCode() 1403 */ 1404 @Override 1405 public int hashCode() { 1406 final int prime = 31; 1407 int result = 1; 1408 result = prime * result + blockNum; 1409 result = prime * result + ca1Length; 1410 result = prime * result + ca2Length; 1411 result = prime * result + Arrays.hashCode(optAln); 1412 result = prime * result + Arrays.hashCode(optLen); 1413 result = prime * result + optLength; 1414 return result; 1415 } 1416 1417 /** 1418 * A week equality metric. 1419 * 1420 * Checks if the optAlign is the same, and if the objects being compared 1421 * seem to be the same (same names, lengths). Does not check properties 1422 * of the alignment such as scores or superposition matrices. 1423 * @see java.lang.Object#equals(java.lang.Object) 1424 */ 1425 @Override 1426 public boolean equals(Object obj) { 1427 if (this == obj) 1428 return true; 1429 if (obj == null) 1430 return false; 1431 if (getClass() != obj.getClass()) 1432 return false; 1433 AFPChain other = (AFPChain) obj; 1434 if (blockNum != other.blockNum) 1435 return false; 1436 if (ca1Length != other.ca1Length) 1437 return false; 1438 if (ca2Length != other.ca2Length) 1439 return false; 1440 if (!Arrays.deepEquals(optAln, other.optAln)) 1441 return false; 1442 if (!Arrays.equals(optLen, other.optLen)) 1443 return false; 1444 if (optLength != other.optLength) 1445 return false; 1446 return true; 1447 } 1448 1449 1450}