1+ /*
2+ * BioJava development code
3+ *
4+ * This code may be freely distributed and modified under the
5+ * terms of the GNU Lesser General Public Licence. This should
6+ * be distributed with the code. If you do not have a copy,
7+ * see:
8+ *
9+ * http://www.gnu.org/copyleft/lesser.html
10+ *
11+ * Copyright for this code is held jointly by the individual
12+ * authors. These should be listed in @author doc comments.
13+ *
14+ * For more information on the BioJava project and its aims,
15+ * or to join the biojava-l mailing list, visit the home page
16+ * at:
17+ *
18+ * http://www.biojava.org/
19+ *
20+ * Created on 07-20-2017
21+ *
22+ * @author Luke Czapla
23+ *
24+ */
125package org .biojava .nbio .structure .basepairs ;
226
327import org .biojava .nbio .structure .*;
1135import java .io .ByteArrayInputStream ;
1236import java .io .IOException ;
1337import java .io .Serializable ;
14- import java .util .*;
38+ import java .util .List ;
39+ import java .util .Arrays ;
40+ import java .util .ArrayList ;
41+ import java .util .Map ;
42+ import java .util .HashMap ;
1543
1644import org .slf4j .Logger ;
1745import org .slf4j .LoggerFactory ;
1846
19- import static java .lang .Math .*;
47+ import static java .lang .Math .sin ;
48+ import static java .lang .Math .cos ;
49+ import static java .lang .Math .atan2 ;
50+ import static java .lang .Math .acos ;
51+ import static java .lang .Math .PI ;
2052
2153/**
2254 * Contributed to BioJava under its LGPL
@@ -104,11 +136,7 @@ public class BasePairParameters implements Serializable {
104136 map .put ("DG" , 1 ); map .put ("GUA" , 1 ); map .put ("G" , 1 );
105137 map .put ("DT" , 2 ); map .put ("THY" , 2 ); map .put ("T" , 2 ); map .put ("U" , 2 ); map .put ("URA" , 2 );
106138 map .put ("DC" , 3 ); map .put ("CYT" , 3 ); map .put ("C" , 3 );
107- // chemically modified bases, leaving out to ignore (to treat as gaps) right now.
108- //map.put("DZM", 0);
109- //map.put("UCL", 2);
110- //map.put("2DT", 2);
111- //map.put("1CC", 3); map.put("5CM", 3);
139+
112140 ringMap = new HashMap <>();
113141 ringMap .put (0 , Arrays .asList ("C8" , "C2" , "N3" , "C4" , "C5" , "C6" , "N7" , "N1" , "N9" ));
114142 ringMap .put (1 , Arrays .asList ("C8" , "C2" , "N3" , "C4" , "C5" , "C6" , "N7" , "N1" , "N9" ));
@@ -191,7 +219,7 @@ public BasePairParameters analyze() {
191219 if (i != 0 ) {
192220 lastStep .invert ();
193221 lastStep .mul (currentStep );
194- double [] sparms = calculatetp (lastStep );
222+ double [] sparms = calculateTp (lastStep );
195223 for (int j = 0 ; j < 6 ; j ++) stepParameters [i ][j ] = sparms [j ];
196224 }
197225 }
@@ -205,7 +233,7 @@ public BasePairParameters analyze() {
205233 * @return An integer value, number of base pairs
206234 */
207235 public int getLength () {
208- if (structure == null || pairParameters == null ) throw new IllegalArgumentException ();
236+ if (structure == null || pairParameters == null ) throw new IllegalArgumentException ("Base pair number is out of range." );
209237 return pairingParameters .length ;
210238 }
211239
@@ -261,7 +289,7 @@ public List<Matrix4d> getReferenceFrames() {
261289 * @return the value as a double (in degrees)
262290 */
263291 public Double getBuckle (int bp ) {
264- if (bp < 0 || bp >= getPairingParameters ().length ) throw new IllegalArgumentException ();
292+ if (bp < 0 || bp >= getPairingParameters ().length ) throw new IllegalArgumentException ("Base pair number is out of range." );
265293 return pairingParameters [bp ][0 ];
266294 }
267295
@@ -271,7 +299,7 @@ public Double getBuckle(int bp) {
271299 * @return the value as a double (in degrees)
272300 */
273301 public Double getPropeller (int bp ) {
274- if (bp < 0 || bp >= getPairingParameters ().length ) throw new IllegalArgumentException ();
302+ if (bp < 0 || bp >= getPairingParameters ().length ) throw new IllegalArgumentException ("Base pair number is out of range." );
275303 return pairingParameters [bp ][1 ];
276304 }
277305
@@ -281,7 +309,7 @@ public Double getPropeller(int bp) {
281309 * @return the value as a double (in degrees)
282310 */
283311 public Double getOpening (int bp ) {
284- if (bp < 0 || bp >= getPairingParameters ().length ) throw new IllegalArgumentException ();
312+ if (bp < 0 || bp >= getPairingParameters ().length ) throw new IllegalArgumentException ("Base pair number is out of range." );
285313 return pairingParameters [bp ][2 ];
286314 }
287315
@@ -291,7 +319,7 @@ public Double getOpening(int bp) {
291319 * @return the value as a double (in Å)
292320 */
293321 public Double getShear (int bp ) {
294- if (bp < 0 || bp >= getPairingParameters ().length ) throw new IllegalArgumentException ();
322+ if (bp < 0 || bp >= getPairingParameters ().length ) throw new IllegalArgumentException ("Base pair number is out of range." );
295323 return pairingParameters [bp ][3 ];
296324 }
297325
@@ -301,7 +329,7 @@ public Double getShear(int bp) {
301329 * @return the value as a double (in Å)
302330 */
303331 public Double getStretch (int bp ) {
304- if (bp < 0 || bp >= getPairingParameters ().length ) throw new IllegalArgumentException ();
332+ if (bp < 0 || bp >= getPairingParameters ().length ) throw new IllegalArgumentException ("Base pair number is out of range." );
305333 return pairingParameters [bp ][4 ];
306334 }
307335
@@ -311,7 +339,7 @@ public Double getStretch(int bp) {
311339 * @return the value as a double (in Å)
312340 */
313341 public Double getStagger (int bp ) {
314- if (bp < 0 || bp >= getPairingParameters ().length ) throw new IllegalArgumentException ();
342+ if (bp < 0 || bp >= getPairingParameters ().length ) throw new IllegalArgumentException ("Base pair number is out of range." );
315343 return pairingParameters [bp ][5 ];
316344 }
317345
@@ -321,7 +349,7 @@ public Double getStagger(int bp) {
321349 * @return the value as a double (in degrees)
322350 */
323351 public Double getTilt (int bp ) {
324- if (bp < 0 || bp >= getStepParameters ().length ) throw new IllegalArgumentException ();
352+ if (bp < 0 || bp >= getStepParameters ().length ) throw new IllegalArgumentException ("Base pair number is out of range." );
325353 return stepParameters [bp ][0 ];
326354 }
327355
@@ -331,7 +359,7 @@ public Double getTilt(int bp) {
331359 * @return the value as a double (in degrees)
332360 */
333361 public Double getRoll (int bp ) {
334- if (bp < 0 || bp >= getStepParameters ().length ) throw new IllegalArgumentException ();
362+ if (bp < 0 || bp >= getStepParameters ().length ) throw new IllegalArgumentException ("Base pair number is out of range." );
335363 return stepParameters [bp ][1 ];
336364 }
337365
@@ -341,7 +369,7 @@ public Double getRoll(int bp) {
341369 * @return the value as a double (in degrees)
342370 */
343371 public Double getTwist (int bp ) {
344- if (bp < 0 || bp >= getStepParameters ().length ) throw new IllegalArgumentException ();
372+ if (bp < 0 || bp >= getStepParameters ().length ) throw new IllegalArgumentException ("Base pair number is out of range." );
345373 return stepParameters [bp ][2 ];
346374 }
347375
@@ -351,7 +379,7 @@ public Double getTwist(int bp) {
351379 * @return the value as a double (in Å)
352380 */
353381 public Double getShift (int bp ) {
354- if (bp < 0 || bp >= getStepParameters ().length ) throw new IllegalArgumentException ();
382+ if (bp < 0 || bp >= getStepParameters ().length ) throw new IllegalArgumentException ("Base pair number is out of range." );
355383 return stepParameters [bp ][3 ];
356384 }
357385
@@ -361,7 +389,7 @@ public Double getShift(int bp) {
361389 * @return the value as a double (in Å)
362390 */
363391 public Double getSlide (int bp ) {
364- if (bp < 0 || bp >= getStepParameters ().length ) throw new IllegalArgumentException ();
392+ if (bp < 0 || bp >= getStepParameters ().length ) throw new IllegalArgumentException ("Base pair number is out of range." );
365393 return stepParameters [bp ][4 ];
366394 }
367395
@@ -371,7 +399,7 @@ public Double getSlide(int bp) {
371399 * @return the value as a double (in Å)
372400 */
373401 public Double getRise (int bp ) {
374- if (bp < 0 || bp >= getStepParameters ().length ) throw new IllegalArgumentException ();
402+ if (bp < 0 || bp >= getStepParameters ().length ) throw new IllegalArgumentException ("Base pair number is out of range." );
375403 return stepParameters [bp ][5 ];
376404 }
377405
@@ -416,7 +444,9 @@ public List<Pair<Group>> findPairs(List<Chain> chains) {
416444 for (int j = i +1 ; j < chains .size (); j ++) {
417445 String complement = complement (chains .get (j ).getAtomSequence (), useRNA );
418446 String match = longestCommonSubstring (c .getAtomSequence (), complement );
419- //log.info(c.getAtomSequence() + " " + chains.get(j).getAtomSequence() + " " + match);
447+ if (log .isDebugEnabled ()) {
448+ log .debug (c .getAtomSequence () + " " + chains .get (j ).getAtomSequence () + " " + match );
449+ }
420450 int index1 = c .getAtomSequence ().indexOf (match );
421451 int index2 = complement .length () - complement .indexOf (match ) - 1 ;
422452 for (int k = 0 ; k < match .length (); k ++) {
@@ -521,11 +551,10 @@ public Matrix4d basePairReferenceFrame(Pair<Group> pair) {
521551 }
522552 assert count == std2 .getAtoms ().size ();
523553
524- // log.info(ref1);
525554 Matrix4d temp = (Matrix4d )ref1 .clone ();
526555 Matrix4d temp2 = (Matrix4d )temp .clone ();
527556 Matrix4d ref2 = sp .superposeAndTransform (pointact , pointref );
528- // log.info(ref2);
557+
529558 double [][] v = new double [3 ][4 ];
530559 double [] y3 = new double [4 ];
531560 double [] z3 = new double [4 ];
@@ -568,7 +597,7 @@ public Matrix4d basePairReferenceFrame(Pair<Group> pair) {
568597 // calculate pairing parameters: buckle, propeller, opening, shear, stretch, stagger
569598 temp2 .invert ();
570599 temp2 .mul (ref2 );
571- pairParameters = calculatetp (temp2 );
600+ pairParameters = calculateTp (temp2 );
572601 for (int i = 0 ; i < 6 ; i ++) pairParameters [i ] *= -1 ;
573602
574603 // return the central frame of the base pair
@@ -595,13 +624,14 @@ public String toString() {
595624 }
596625
597626
627+ // The following methods are just helper classes for the rapid analyze of base-pair geometry.
598628 /**
599- * This method calculates pairing and step parameters from 4x4 transformation matrices
629+ * This method calculates pairing and step parameters from 4x4 transformation matrices (used internally)
600630 * that come out as Matrix4d;
601631 * @param input the 4x4 matrix representing the transformation from strand II -> strand I or pair i to pair i+1
602632 * @return Six parameters as double[6]
603633 */
604- public static double [] calculatetp (Matrix4d input ) {
634+ public static double [] calculateTp (Matrix4d input ) {
605635
606636 double [][] A = new double [4 ][4 ];
607637 for (int i = 0 ; i < 4 ; i ++) for (int j = 0 ; j < 4 ; j ++) {
@@ -646,8 +676,13 @@ public static double[] calculatetp(Matrix4d input) {
646676
647677 }
648678
649-
650- public static char complementBase (char base , boolean RNA ) {
679+ /**
680+ * Return the complement of a base (used internally)
681+ * @param base The letter of the base
682+ * @param RNA Whether it is RNA (if false, it is DNA)
683+ * @return The character representing the complement of the base
684+ */
685+ protected static char complementBase (char base , boolean RNA ) {
651686 if (base == 'A' && RNA ) return 'U' ;
652687 if (base == 'A' ) return 'T' ;
653688 if (base == 'T' && !RNA ) return 'A' ;
@@ -657,15 +692,26 @@ public static char complementBase(char base, boolean RNA) {
657692 return ' ' ;
658693 }
659694
660- public static String complement (String sequence , boolean RNA ) {
695+ /**
696+ * Simple helper method for quickly checking the complement of a sequence, see also DNASequence nad RNASequence classes
697+ * for more extensively useful functions not used in this narrow context of structural biology of base pairs. (Used internally)
698+ */
699+ private static String complement (String sequence , boolean RNA ) {
661700 String result = "" ;
662701 for (int i = sequence .length () - 1 ; i >= 0 ; i --) {
663702 result += complementBase (sequence .charAt (i ), RNA );
664703 }
665704 return result ;
666705 }
667706
668- public static double [] cross (double [] a , double [] b ) {
707+ /**
708+ * 3D Vector cross product of two vectors as double arrays (used internally)
709+ *
710+ * @param a An array of length 3 or 4 (4th component is ignored)
711+ * @param b An array of length 3 or 4 (4th component is ignored)
712+ * @return The cross product of the vectors (just the first three components
713+ */
714+ private static double [] cross (double [] a , double [] b ) {
669715 assert a .length >= 3 && b .length >= 3 ;
670716 double [] result = new double [4 ];
671717 result [0 ] = a [1 ]*b [2 ]-a [2 ]*b [1 ];
@@ -674,7 +720,13 @@ public static double[] cross(double[] a, double[] b) {
674720 return result ;
675721 }
676722
677- public static double [] removeComponent (double [] a , double [] b ) {
723+ /**
724+ * Remove any component of vector a that is along vector b (used internally)
725+ * @param a The array (vector) to remove component from
726+ * @param b The component array (vector) to remove from the first
727+ * @return The original array a with any component along b removed from it.
728+ */
729+ private static double [] removeComponent (double [] a , double [] b ) {
678730 double dot = 0 ;
679731 double [] result = new double [4 ];
680732 for (int i = 0 ; i < 3 ; i ++) {
@@ -687,7 +739,13 @@ public static double[] removeComponent(double[] a, double[] b) {
687739
688740 }
689741
690- public static String longestCommonSubstring (String s1 , String s2 ) {
742+ /**
743+ * Finds the longest common substring between two strings (used internally)
744+ * @param s1 The first string
745+ * @param s2 The second string
746+ * @return The substring itself
747+ */
748+ private static String longestCommonSubstring (String s1 , String s2 ) {
691749 int start = 0 ;
692750 int max = 0 ;
693751 for (int i = 0 ; i < s1 .length (); i ++) {
@@ -706,6 +764,13 @@ public static String longestCommonSubstring(String s1, String s2) {
706764 return s1 .substring (start , (start + max ));
707765 }
708766
767+ /**
768+ * Return true if a is the complement of b (used internally)
769+ * @param a First letter
770+ * @param b Potential matching letter
771+ * @param RNA Whether it is RNA (if false, DNA rules are used)
772+ * @return True if the bases are complementary.
773+ */
709774 protected static boolean match (char a , char b , boolean RNA ) {
710775 if (a == 'A' && b == 'T' && !RNA ) return true ;
711776 if (a == 'A' && b == 'U' && RNA ) return true ;
0 commit comments