gnGenomeSpec.cpp Source File

Main Page Namespace List Class Hierarchy Alphabetical List Compound List File List Compound Members File Members

# gnGenomeSpec.cpp

Go to the documentation of this file.

    00001 /////////////////////////////////////////////////////////////////////////////
    00002 // File:            gnGenomeSpec.cpp
    00003 // Purpose:         implements gnMultiSpec for genomes
    00004 // Description:
    00005 // Changes:
    00006 // Version:         libGenome 0.5.1
    00007 // Author:          Aaron Darling
    00008 // Modified by:
    00009 // Copyright:       (c) Aaron Darling
    00010 // Licenses:        See COPYING file for details
    00011 /////////////////////////////////////////////////////////////////////////////
    00012
    00013 #include "gn/gnGenomeSpec.h"
    00014 #include <string>
    00015
    00016 gnGenomeSpec::gnGenomeSpec()
    00017 {
    00018         gnBaseSpec::Clear();
    00019 }
    00020
    00021 gnGenomeSpec::gnGenomeSpec( const gnGenomeSpec& s )
    00022 {
    00023         m_sourceName = s.m_sourceName;
    00024         m_name = s.m_name;
    00025         m_reverseComplement = s.m_reverseComplement;
    00026         m_circular = s.m_circular;
    00027         //copy the header list.
    00028         uint32 list_size =  s.m_headerList.size();
    00029         m_headerList.reserve(list_size);
    00030         for(uint32 i=0; i < list_size; i++)
    00031                 m_headerList.push_back(s.m_headerList[i]->Clone());
    00032         //copy the fragment list.
    00033         list_size =  s.m_SpecList.size();
    00034         m_SpecList.reserve(list_size);
    00035         for(uint32 i=0; i < list_size; i++)
    00036                 m_SpecList.push_back(s.m_SpecList[i]->Clone());
    00037 }
    00038 gnGenomeSpec::~gnGenomeSpec()
    00039 {
    00040         Clear();
    00041 }
    00042 // Clone
    00043 void gnGenomeSpec::Clear()
    00044 {
    00045         uint32 list_size = m_SpecList.size();
    00046         for(uint32 i=0; i < list_size; i++)
    00047                 delete m_SpecList[i];
    00048         m_SpecList.clear();
    00049         gnMultiSpec::Clear();
    00050 }
    00051
    00052 void gnGenomeSpec::SetReverseComplement( const boolean value )
    00053 {
    00054         if(value == m_reverseComplement)
    00055                 return;
    00056         //reverse the spec list entries
    00057         vector<gnFragmentSpec*> tmp_spec_list;
    00058         for(uint32 i=0; i < GetSpecListLength(); i++){
    00059                 //transmit rev_comp down to each fragment spec
    00060                 GetSpec(i)->SetReverseComplement(!GetSpec(i)->IsReverseComplement());
    00061                 tmp_spec_list.insert(tmp_spec_list.begin(), GetSpec(i));
    00062         }
    00063         m_SpecList = tmp_spec_list;
    00064         m_reverseComplement = value;
    00065 }
    00066
    00067 gnGenomeSpec* gnGenomeSpec::CloneRange( const gnSeqI startI, const gnSeqI len ) const{
    00068         if(len == 0)
    00069                 return new gnGenomeSpec();
    00070
    00071         //find the valid range of specs to copy
    00072         uint32 firstSpec = GetSpecIndexByBase(startI);
    00073         gnSeqI total_copylen = len;
    00074         uint32 endSpec;
    00075         if(len != GNSEQI_END){
    00076                 endSpec = GetSpecIndexByBase(startI + len - 1);
    00077         }else{
    00078                 endSpec = GetSpecListLength() - 1;
    00079                 total_copylen = GetLength() - startI;
    00080         }
    00081
    00082         //find their starting and ending bases
    00083         gnSeqI firstBase = startI - GetSpecStartBase(firstSpec);
    00084         gnSeqI firstSpecLen = GetSpec(firstSpec)->GetLength();
    00085         boolean spans_specs = true;
    00086         gnSeqI firstCopyLen = firstSpecLen - firstBase;
    00087         if(firstCopyLen >= total_copylen){
    00088                 spans_specs = false;
    00089                 firstCopyLen = total_copylen;
    00090         }
    00091
    00092         gnGenomeSpec* destSpec = new gnGenomeSpec();
    00093         gnFragmentSpec* newSpec = m_SpecList[firstSpec]->CloneRange(firstBase, firstCopyLen);
    00094         destSpec->AddSpec( newSpec );
    00095
    00096         gnSeqI cur_copylen = firstCopyLen;
    00097         //add all the completely covered specs in the middle
    00098         for(uint32 specI = firstSpec + 2; specI <= endSpec; specI++){
    00099                 destSpec->AddSpec(GetSpec(specI-1)->Clone());
    00100                 cur_copylen += GetSpec(specI-1)->GetLength();
    00101         }
    00102         //add the last spec if necessary
    00103         if(spans_specs){
    00104                 newSpec = m_SpecList[endSpec]->CloneRange( 0, total_copylen - cur_copylen);
    00105                 destSpec->AddSpec(newSpec);
    00106         }
    00107         return destSpec;
    00108 }
    00109
    00110
    00111 //IMPLEMENT ME: What to do with headers?
    00112 void gnGenomeSpec::MergeFragments(const uint32 startF, const uint32 endF){
    00113         if(startF > m_SpecList.size() || endF > m_SpecList.size())
    00114                 Throw_gnEx(FragmentIndexOutOfBounds());
    00115         if(startF > endF)
    00116                 Throw_gnEx(FragmentIndexOutOfBounds());
    00117
    00118         for(uint32 i = startF + 1; i < endF; i++){
    00119                 gnFragmentSpec* delspec = m_SpecList[startF + 1];
    00120                 m_SpecList.erase(m_SpecList.begin() + startF + 1);
    00121
    00122                 for(uint32 j = 0; j < delspec->GetSpecListLength(); j++)
    00123                         m_SpecList[startF]->AddSpec(delspec->GetSpec(j));
    00124                 delete delspec;
    00125         }
    00126 }
    00127
    00128 uint32 gnGenomeSpec::AddFeature( gnBaseFeature* feat ){
    00129         uint32 count = 0;
    00130         uint32 len = 0;
    00131         uint32 featureI = 0;
    00132         uint32 specListLen = GetSpecListLength();
    00133
    00134         for(uint32 specI = 0; specI < specListLen; specI++){
    00135                 len = GetSpec(specI)->GetLength();
    00136                 gnLocation lt(count, count+len);
    00137                 if(feat->IsContainedBy(lt)){
    00138                         return featureI + GetSpec(specI)->AddFeature(feat);
    00139                 }
    00140                 count += len;
    00141                 featureI += GetSpec(specI)->GetFeatureListLength();
    00142         }
    00143         //if we get this far then the feature has invalid coordinates
    00144         Throw_gnEx(SeqIndexOutOfBounds());
    00145 }
    00146
    00147 uint32 gnGenomeSpec::GetFeatureListLength() const
    00148 {
    00149         uint32 len = 0;
    00150         for(uint32 i=0; i < GetSpecListLength(); i++)
    00151                 len += GetSpec(i)->GetFeatureListLength();
    00152         return len;
    00153 }
    00154
    00155 gnBaseFeature* gnGenomeSpec::GetFeature(const uint32 i ) const
    00156 {
    00157         uint32 count = 0;
    00158         uint32 len = 0;
    00159         for(uint32 specI=0; specI < GetSpecListLength(); specI++){
    00160                 len = GetSpec(specI)->GetFeatureListLength();
    00161                 if(count <= i && i < count + len){
    00162                         gnBaseFeature* feat = GetSpec(specI)->GetFeature(i - count);
    00163                         feat->MovePositive(GetSpecStartBase(specI));
    00164                         return feat;
    00165                 }
    00166                 count += len;
    00167         }
    00168         Throw_gnEx(FeatureIndexOutOfBounds());
    00169 }
    00170
    00171 void gnGenomeSpec::GetContainedFeatures(const gnLocation& lt, vector<gnBaseFeature*>& feature_vector, vector<uint32>& index_vector) const{
    00172         uint32 ss_size = GetSpecListLength();
    00173         uint32 fl_size = 0;
    00174         gnSeqI start_base = 0;
    00175         for(uint32 i=0; i < ss_size; i++){
    00176                 gnLocation sub_lt = lt;
    00177                 gnSeqI sub_len = GetSpec(i)->GetLength();
    00178                 sub_lt.MoveNegative(start_base);
    00179                 sub_lt.CropEnd(sub_len);
    00180                 GetSpec(i)->GetContainedFeatures(sub_lt, feature_vector, index_vector);
    00181                 uint32 fvs = feature_vector.size();
    00182                 for(uint32 j = 0; j < fvs; j++){
    00183                         feature_vector[j]->MovePositive(start_base);
    00184                         index_vector[j]+= fl_size;
    00185                 }
    00186                 if(fvs > 0)
    00187                         return;
    00188                 start_base += sub_len;
    00189                 fl_size += GetSpec(i)->GetFeatureListLength();
    00190         }
    00191 }
    00192
    00193 void gnGenomeSpec::GetIntersectingFeatures(const gnLocation& lt, vector<gnBaseFeature*>& feature_vector, vector<uint32>& index_vector) const{
    00194         uint32 ss_size = GetSpecListLength();
    00195         uint32 fl_size = 0;
    00196         gnSeqI start_base = 0;
    00197         for(uint32 i=0; i < ss_size; i++){
    00198                 gnLocation sub_lt = lt;
    00199                 gnSeqI sub_len = GetSpec(i)->GetLength();
    00200                 sub_lt.MoveNegative(start_base);
    00201                 sub_lt.CropEnd(sub_len);
    00202                 GetSpec(i)->GetIntersectingFeatures(sub_lt, feature_vector, index_vector);
    00203                 uint32 fvs = feature_vector.size();
    00204                 for(uint32 j = 0; j < fvs; j++){
    00205                         feature_vector[j]->MovePositive(start_base);
    00206                         index_vector[j]+= fl_size;
    00207                 }
    00208                 if(fvs > 0)
    00209                         return;
    00210                 start_base += sub_len;
    00211                 fl_size += GetSpec(i)->GetFeatureListLength();
    00212         }
    00213 }
    00214 void gnGenomeSpec::GetBrokenFeatures(const gnLocation& lt, vector<gnBaseFeature*>& feature_vector) const{
    00215         uint32 ss_size = GetSpecListLength();
    00216         uint32 fl_size = 0;
    00217         gnSeqI start_base = 0;
    00218         for(uint32 i=0; i < ss_size; i++){
    00219                 gnLocation sub_lt = lt;
    00220                 gnSeqI sub_len = GetSpec(i)->GetLength();
    00221                 sub_lt.MoveNegative(start_base);
    00222                 sub_lt.CropEnd(sub_len);
    00223                 GetSpec(i)->GetBrokenFeatures(sub_lt, feature_vector);
    00224                 uint32 fvs = feature_vector.size();
    00225                 for(uint32 j = 0; j < fvs; j++)
    00226                         feature_vector[j]->MovePositive(start_base);
    00227                 if(fvs > 0)
    00228                         return;
    00229                 start_base += sub_len;
    00230                 fl_size += GetSpec(i)->GetFeatureListLength();
    00231         }
    00232 }
    00233
    00234 void gnGenomeSpec::RemoveFeature( const uint32 i ){
    00235         uint32 count = 0;
    00236         uint32 len = 0;
    00237         uint32 specI=0;
    00238         for(; specI < GetSpecListLength(); specI++){
    00239                 len = GetSpec(specI)->GetFeatureListLength();
    00240                 if(count <= i && i < count + len){
    00241                         GetSpec(specI)->RemoveFeature( i - count);
    00242                 }
    00243                 count += len;
    00244         }
    00245         Throw_gnEx(FeatureIndexOutOfBounds());
    00246 }