All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.hfg.bio.seq.ProteinXLink Maven / Gradle / Ivy

There is a newer version: 20240423
Show newest version
package com.hfg.bio.seq;

import java.util.Map;

import com.hfg.bio.AminoAcid;
import com.hfg.chem.Element;
import com.hfg.bio.HfgBioXML;
import com.hfg.chem.Molecule;
import com.hfg.util.CompareUtil;
import com.hfg.xml.XMLNode;
import com.hfg.xml.XMLTag;

//------------------------------------------------------------------------------
/**
 * Biological protein sequence crosslink.
 *
 * @author J. Alex Taylor, hairyfatguy.com
 */
//------------------------------------------------------------------------------
// com.hfg XML/HTML Coding Library
//
// This library is free software; you can redistribute it and/or
// modify it under the terms of the GNU Lesser General Public
// License as published by the Free Software Foundation; either
// version 2.1 of the License, or (at your option) any later version.
//
// This library 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
// Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public
// License along with this library; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
//
// J. Alex Taylor, President, Founder, CEO, COO, CFO, OOPS hairyfatguy.com
// [email protected]
//------------------------------------------------------------------------------


public class ProteinXLink extends Molecule implements Cloneable, Comparable
{

   private ProteinXLinkType mType;
   private Protein          mDonorChain;
   private String           mDonorChainId;
   private Integer          mDonorPosition;
   private Protein          mAcceptorChain;
   private String           mAcceptorChainId;
   private Integer          mAcceptorPosition;

   private char             mDonorResidue;
   private char             mAcceptorResidue;

   private Protein          mParentProtein;

   //##########################################################################
   // CONSTRUCTORS
   //##########################################################################

   //--------------------------------------------------------------------------
   public ProteinXLink(ProteinXLinkType inType, Protein inDonorChain, int inDonorPosition, Protein inAcceptorChain, int inAcceptorPosition)
   {
      mType             = inType;
      mDonorChain       = inDonorChain;
      mDonorChainId     = inDonorChain.getID();
      mDonorPosition    = inDonorPosition;
      mAcceptorChain    = inAcceptorChain;
      mAcceptorChainId  = inAcceptorChain.getID();
      mAcceptorPosition = inAcceptorPosition;

      mDonorResidue     = inDonorChain.residueAt(inDonorPosition);
      mAcceptorResidue  = inAcceptorChain.residueAt(inAcceptorPosition);

      validate();
   }

   //--------------------------------------------------------------------------
   public ProteinXLink(XMLNode inXML)
   {
      if (! inXML.getTagName().equals(HfgBioXML.XLINK_TAG))
      {
         throw new RuntimeException("Cannot construct an " + this.getClass().getSimpleName() + " from a " + inXML.getTagName() + " tag!");
      }

      mType = new ProteinXLinkType(inXML.getRequiredSubtagByName(HfgBioXML.XLINK_TYPE_TAG));

      XMLNode donorTag = inXML.getRequiredSubtagByName(HfgBioXML.DONOR_TAG);
      mDonorChainId = donorTag.getAttributeValue(HfgBioXML.CHAIN_ID_ATT);
      mDonorPosition = Integer.parseInt(donorTag.getAttributeValue(HfgBioXML.RESIDUE_NUM_ATT));
      mDonorResidue = donorTag.getAttributeValue(HfgBioXML.RESIDUE_ATT).charAt(0);

      XMLNode acceptorTag = inXML.getRequiredSubtagByName(HfgBioXML.ACCEPTOR_TAG);
      mAcceptorChainId = acceptorTag.getAttributeValue(HfgBioXML.CHAIN_ID_ATT);
      mAcceptorPosition = Integer.parseInt(acceptorTag.getAttributeValue(HfgBioXML.RESIDUE_NUM_ATT));
      mAcceptorResidue = acceptorTag.getAttributeValue(HfgBioXML.RESIDUE_ATT).charAt(0);
   }

   //##########################################################################
   // PUBLIC METHODS
   //##########################################################################

   //---------------------------------------------------------------------------
   @Override
   public ProteinXLink clone()
   {
      ProteinXLink copy = (ProteinXLink) super.clone();

      return copy;
   }

   //--------------------------------------------------------------------------
   public ProteinXLinkChainLinkage getChainLinkage()
   {
      return (0 == CompareUtil.compare(getDonorChainId(), getAcceptorChainId()) ? ProteinXLinkChainLinkage.INTRACHAIN : ProteinXLinkChainLinkage.INTERCHAIN);
   }

   //--------------------------------------------------------------------------
   public ProteinXLinkType getType()
   {
      return mType;
   }


   //--------------------------------------------------------------------------
   public String getDonorChainId()
   {
      return mDonorChainId;
   }

   //--------------------------------------------------------------------------
   protected ProteinXLink setDonorChainId(String inValue)
   {
      mDonorChainId = inValue;
      return this;
   }


   //--------------------------------------------------------------------------
   public int getDonorPosition()
   {
      return mDonorPosition;
   }


   //--------------------------------------------------------------------------
   public String getAcceptorChainId()
   {
      return mAcceptorChainId;
   }

   //--------------------------------------------------------------------------
   protected ProteinXLink setAcceptorChainId(String inValue)
   {
      mAcceptorChainId = inValue;
      return this;
   }


   //--------------------------------------------------------------------------
   public int getAcceptorPosition()
   {
      return mAcceptorPosition;
   }

   //--------------------------------------------------------------------------
   public String toString()
   {
      return mType.name() + ": " + (mDonorChainId != null ? mDonorChainId : "") + " " + mDonorResidue + mDonorPosition + "  -->  "
                              + (mAcceptorChainId != null ? mAcceptorChainId : "") + " " + mAcceptorResidue + mAcceptorPosition;
   }

   //--------------------------------------------------------------------------
   public XMLNode toXMLNode()
   {
      XMLNode node = new XMLTag(HfgBioXML.XLINK_TAG);

      node.addSubtag(mType.toXMLNode());

      XMLNode donorTag = new XMLTag(HfgBioXML.DONOR_TAG);
      node.addSubtag(donorTag);
      donorTag.setAttribute(HfgBioXML.CHAIN_ID_ATT, mDonorChainId);
      donorTag.setAttribute(HfgBioXML.RESIDUE_NUM_ATT, mDonorPosition);
      donorTag.setAttribute(HfgBioXML.RESIDUE_ATT, mDonorResidue);

      XMLNode acceptorTag = new XMLTag(HfgBioXML.ACCEPTOR_TAG);
      node.addSubtag(acceptorTag);
      acceptorTag.setAttribute(HfgBioXML.CHAIN_ID_ATT, mAcceptorChainId);
      acceptorTag.setAttribute(HfgBioXML.RESIDUE_NUM_ATT, mAcceptorPosition);
      acceptorTag.setAttribute(HfgBioXML.RESIDUE_ATT, mAcceptorResidue);


      return node;
   }

   //--------------------------------------------------------------------------
   /**
    Returns an unmodifiable copy of the elemental composition Map. The keys are
    Element objects and the values are Floats. Why Floats instead of Integers you
    ask? Because some amino acid codes such as B and Z are ambiguous averages.
    @return an elemental composition map
    */
   public Map getElementalComposition()
   {
      return mType.getElementalComposition();
   }

   //--------------------------------------------------------------------------
   public Double getMonoisotopicMass()
   {
      return mType.getMonoisotopicMass();
   }

   //--------------------------------------------------------------------------
   public Double getAverageMass()
   {
      return mType.getAverageMass();
   }

   //--------------------------------------------------------------------------
   public Double getOrganicAverageMass()
   {
      return mType.getOrganicAverageMass();
   }

   //--------------------------------------------------------------------------
   /**
    Sets the protein container to which this x-link belongs.
    @param inParentProtein the protein to which this x-link belongs
    */
   protected void setParentProtein(Protein inParentProtein)
   {
      if (inParentProtein != null)
      {
         // Validate that the donor chain is present in the parent protein.
         if (mDonorChain != null)
         {
            if (inParentProtein != mDonorChain
                && null == inParentProtein.getChain(mDonorChainId))
            {
               throw new RuntimeException("Donor chain '" + mDonorChainId + "' is not present in this Protein!");
            }
         }
         else
         {
            mDonorChain = inParentProtein.getChain(mDonorChainId);
            if (null == mDonorChain)
            {
               throw new RuntimeException("Donor chain '" + mDonorChainId + "' is not present in this Protein!");
            }
         }

         // Validate that the acceptor chain is present in the parent protein.
         if (mAcceptorChain != null)
         {
            if (inParentProtein != mAcceptorChain
                && null == inParentProtein.getChain(mAcceptorChainId))
            {
               throw new RuntimeException("Acceptor chain '" + mAcceptorChainId + "' is not present in this Protein!");
            }
         }
         else
         {
            mAcceptorChain = inParentProtein.getChain(mAcceptorChainId);
            if (null == mAcceptorChain)
            {
               throw new RuntimeException("Acceptor chain '" + mAcceptorChainId + "' is not present in this Protein!");
            }
         }

         // Be sure the donor residue is not already occupied
         // TODO

         // Be sure the acceptor residue is not already occupied
         // TODO
      }

      mParentProtein = inParentProtein;
   }

   //--------------------------------------------------------------------------
   protected void validate()
   {
      AminoAcid donor    = mDonorChain.aminoAcidAt(mDonorPosition);
      AminoAcid acceptor = mAcceptorChain.aminoAcidAt(mAcceptorPosition);
      if (! mType.isAcceptableSite(donor, acceptor))
      {
         throw new RuntimeException("Not a valid X-Link!\n" + this);
      }
   }

   //--------------------------------------------------------------------------
   @Override
   public boolean equals(Object inObj)
   {
      return inObj instanceof ProteinXLink ? compareTo(inObj) == 0 : false;
   }

   //--------------------------------------------------------------------------
   @Override
   public int hashCode()
   {
      int hashCode = getType().hashCode();
      if (mDonorChainId != null) hashCode += mDonorChainId.hashCode();
      hashCode += mDonorPosition.hashCode();
      if (mAcceptorChainId != null) hashCode += mAcceptorChainId.hashCode();
      hashCode += mAcceptorPosition.hashCode();

      return  hashCode;
   }

   //--------------------------------------------------------------------------
   public int compareTo(Object inObj)
   {
      int result = -1;

      if (inObj != null)
      {
         if (inObj instanceof ProteinXLink)
         {
            ProteinXLink xlink2 = (ProteinXLink) inObj;

            if (mDonorChain != null
                && xlink2.mDonorChain != null)
            {
               result = mDonorChain.compareTo(xlink2.mDonorChain);
            }
            else
            {
               result = CompareUtil.compare(getDonorChainId(), xlink2.getDonorChainId());
            }

            if (0 == result)
            {
               result = mDonorPosition.compareTo(xlink2.mDonorPosition);

               if (0 == result)
               {
                  if (mAcceptorChain != null
                      && xlink2.mAcceptorChain != null)
                  {
                     result = mAcceptorChain.compareTo(xlink2.mAcceptorChain);
                  }
                  else
                  {
                     result = CompareUtil.compare(getAcceptorChainId(), xlink2.getAcceptorChainId());
                  }

                  if (0 == result)
                  {
                     result = mAcceptorPosition.compareTo(xlink2.mAcceptorPosition);
                  }
               }
            }
         }
         else
         {
            result = CompareUtil.compare(hashCode(), inObj.hashCode());
         }
      }

      return result;
   }

}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy