Stepper.hpp

Go to the documentation of this file.
00001 //::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
00002 //
00003 //        This file is part of E-Cell Simulation Environment package
00004 //
00005 //                Copyright (C) 1996-2002 Keio University
00006 //
00007 //::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
00008 //
00009 //
00010 // E-Cell is free software; you can redistribute it and/or
00011 // modify it under the terms of the GNU General Public
00012 // License as published by the Free Software Foundation; either
00013 // version 2 of the License, or (at your option) any later version.
00014 // 
00015 // E-Cell is distributed in the hope that it will be useful,
00016 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00017 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
00018 // See the GNU General Public License for more details.
00019 // 
00020 // You should have received a copy of the GNU General Public
00021 // License along with E-Cell -- see the file COPYING.
00022 // If not, write to the Free Software Foundation, Inc.,
00023 // 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
00024 // 
00025 //END_HEADER
00026 //
00027 // written by Koichi Takahashi <shafi@e-cell.org>,
00028 // E-Cell Project.
00029 //
00030 
00031 #ifndef __STEPPER_HPP
00032 #define __STEPPER_HPP
00033 
00034 //#include <vector>
00035 //#include <algorithm>
00036 //#include <utility>
00037 //#include <iostream>
00038 
00039 #include <gsl/gsl_rng.h>
00040 
00041 #include "libecs.hpp"
00042 
00043 #include "Util.hpp"
00044 #include "Polymorph.hpp"
00045 #include "Interpolant.hpp"
00046 #include "PropertyInterface.hpp"
00047 
00048 
00049 
00050 namespace libecs
00051 {
00052 
00053   /** @addtogroup stepper
00054    *@{
00055    */
00056 
00057   /** @file */
00058 
00059 
00060   //  DECLARE_TYPE( std::valarray<Real>, RealValarray );
00061 
00062   DECLARE_VECTOR( Real, RealVector );
00063 
00064 
00065   /**
00066      Stepper class defines and governs a computation unit in a model.
00067 
00068      The computation unit is defined as a set of Process objects.
00069 
00070   */
00071 
00072 
00073   LIBECS_DM_CLASS( Stepper, PropertiedClass )
00074   {
00075 
00076   public:
00077 
00078     LIBECS_DM_BASECLASS( Stepper );
00079 
00080     LIBECS_DM_OBJECT_ABSTRACT( Stepper )
00081       {
00082         INHERIT_PROPERTIES( PropertiedClass );
00083         
00084         PROPERTYSLOT_SET_GET( Integer,       Priority );
00085         PROPERTYSLOT_SET_GET( Real,      StepInterval );
00086         PROPERTYSLOT_SET_GET( Real,      MaxStepInterval );
00087         PROPERTYSLOT_SET_GET( Real,      MinStepInterval );
00088         PROPERTYSLOT_SET    ( String,    RngSeed );
00089 
00090 
00091         // these properties are not loaded/saved.
00092         PROPERTYSLOT_GET_NO_LOAD_SAVE    ( Real,      CurrentTime );
00093         PROPERTYSLOT_GET_NO_LOAD_SAVE    ( Polymorph, ProcessList );
00094         PROPERTYSLOT_GET_NO_LOAD_SAVE    ( Polymorph, SystemList );
00095         PROPERTYSLOT_GET_NO_LOAD_SAVE    ( Polymorph, ReadVariableList );
00096         PROPERTYSLOT_GET_NO_LOAD_SAVE    ( Polymorph, WriteVariableList );
00097 
00098 
00099         // setting rng type:  not yet supported
00100         //PROPERTYSLOT_SET_GET( Polymorph, Rng,              Stepper );
00101       }
00102 
00103 
00104     class PriorityCompare
00105     {
00106     public:
00107       bool operator()( StepperPtr aLhs, StepperPtr aRhs ) const
00108       {
00109         return compare( aLhs->getPriority(), aRhs->getPriority() );
00110       }
00111 
00112       bool operator()( StepperPtr aLhs, IntegerParam aRhs ) const
00113       {
00114         return compare( aLhs->getPriority(), aRhs );
00115       }
00116 
00117       bool operator()( IntegerParam aLhs, StepperPtr aRhs ) const
00118       {
00119         return compare( aLhs, aRhs->getPriority() );
00120       }
00121 
00122     private:
00123 
00124       // if statement can be faster than returning an expression directly
00125       inline static bool compare( IntegerParam aLhs, IntegerParam aRhs )
00126       {
00127         if( aLhs > aRhs )
00128           {
00129             return true;
00130           }
00131         else
00132           {
00133             return false;
00134           }
00135       }
00136 
00137 
00138     };
00139 
00140 
00141     Stepper(); 
00142     virtual ~Stepper();
00143 
00144 
00145     /**
00146        Get the current time of this Stepper.
00147 
00148        The current time is defined as a next scheduled point in time
00149        of this Stepper.
00150 
00151        @return the current time in Real.
00152     */
00153 
00154     GET_METHOD( Real, CurrentTime )
00155     {
00156       return theCurrentTime;
00157     }
00158 
00159     SET_METHOD( Real, CurrentTime )
00160     {
00161       theCurrentTime = value;
00162     }
00163 
00164     /**
00165        This may be overridden in dynamically scheduled steppers.
00166 
00167     */
00168 
00169     virtual SET_METHOD( Real, StepInterval )
00170     {
00171       Real aNewStepInterval( value );
00172 
00173       if( aNewStepInterval > getMaxStepInterval() )
00174         {
00175           aNewStepInterval = getMaxStepInterval();
00176         }
00177       else if ( aNewStepInterval < getMinStepInterval() )
00178         {
00179           aNewStepInterval = getMinStepInterval();
00180         }
00181 
00182       loadStepInterval( aNewStepInterval );
00183     }
00184 
00185 
00186     /**
00187        Get the step interval of this Stepper.
00188 
00189        The step interval is a length of time that this Stepper proceeded
00190        in the last step.
00191        
00192        @return the step interval of this Stepper
00193     */
00194 
00195 
00196     GET_METHOD( Real, StepInterval )
00197     {
00198       return theStepInterval;
00199     }
00200 
00201     virtual GET_METHOD( Real, TimeScale )
00202     {
00203       return getStepInterval();
00204     }
00205 
00206     SET_METHOD( String, ID )
00207     {
00208       theID = value;
00209     }
00210 
00211     GET_METHOD( String, ID )
00212     {
00213       return theID;
00214     }
00215 
00216 
00217     SET_METHOD( Real, MinStepInterval )
00218     {
00219       theMinStepInterval = value;
00220     }
00221 
00222     GET_METHOD( Real, MinStepInterval )
00223     {
00224       return theMinStepInterval;
00225     }
00226 
00227     SET_METHOD( Real, MaxStepInterval )
00228     {
00229       theMaxStepInterval = value;
00230     }
00231 
00232     GET_METHOD( Real, MaxStepInterval )
00233     {
00234       return theMaxStepInterval;
00235     }
00236 
00237 
00238     ECELL_API GET_METHOD( Polymorph, WriteVariableList );
00239     ECELL_API GET_METHOD( Polymorph, ReadVariableList );
00240     ECELL_API GET_METHOD( Polymorph, ProcessList );
00241     ECELL_API GET_METHOD( Polymorph, SystemList );
00242 
00243     ECELL_API SET_METHOD( String, RngSeed );
00244 
00245     GET_METHOD( String, RngType );
00246 
00247 
00248     /**
00249 
00250     */
00251 
00252     virtual void initialize();
00253 
00254     void initializeProcesses();
00255 
00256 
00257     /**       
00258        Each subclass of Stepper defines this.
00259 
00260        @note Subclass of Stepper must call this by Stepper::calculate() from
00261        their step().
00262     */
00263 
00264     virtual void step() = 0;
00265 
00266     ECELL_API virtual void integrate( RealParam aTime );
00267 
00268     /**
00269        Let the Loggers log data.
00270 
00271        The default behavior is to call all the Loggers attached to
00272        any Entities related to this Stepper.
00273     */
00274 
00275     ECELL_API virtual void log();
00276     
00277     /**
00278        Register a System to this Stepper.
00279 
00280        @param aSystemPtr a pointer to a System object to register
00281     */
00282 
00283     void registerSystem( SystemPtr aSystemPtr );
00284 
00285     /**
00286        Remove a System from this Stepper.
00287 
00288        @note This method is not currently supported.  Calling this method
00289        causes undefined behavior.
00290 
00291        @param aSystemPtr a pointer to a System object
00292     */
00293 
00294     void removeSystem( SystemPtr aSystemPtr );
00295 
00296     /**
00297        Register a Process to this Stepper.
00298 
00299        @param aProcessPtr a pointer to a Process object to register
00300     */
00301 
00302     void registerProcess( ProcessPtr aProcessPtr );
00303 
00304     /**
00305        Remove a Process from this Stepper.
00306 
00307        @note This method is not currently supported.
00308 
00309        @param aProcessPtr a pointer to a Process object
00310     */
00311 
00312     void removeProcess( ProcessPtr aProcessPtr );
00313 
00314 
00315     void loadStepInterval( RealParam aStepInterval )
00316     {
00317       theStepInterval = aStepInterval;
00318     }
00319 
00320     void registerLogger( LoggerPtr );
00321 
00322     ModelPtr getModel() const
00323     {
00324       return theModel;
00325     }
00326 
00327     /**
00328        @internal
00329 
00330     */
00331 
00332     void setModel( ModelPtr const aModel )
00333     {
00334       theModel = aModel;
00335     }
00336 
00337     void setSchedulerIndex( const int anIndex )
00338     {
00339       theSchedulerIndex = anIndex;
00340     }
00341 
00342     const int getSchedulerIndex() const
00343     {
00344       return theSchedulerIndex;
00345     }
00346 
00347 
00348     /**
00349        Set a priority value of this Stepper.
00350 
00351        The priority is an Int value which is used to determine the
00352        order of step when more than one Stepper is scheduled at the
00353        same point in time (such as starting up: t=0).   
00354 
00355        Larger value means higher priority, and called first.
00356 
00357        @param value the priority value as an Int.
00358        @see Scheduler
00359     */
00360 
00361     SET_METHOD( Integer, Priority )
00362     {
00363       thePriority = value;
00364     }
00365 
00366     /**
00367        @see setPriority()
00368     */
00369 
00370     GET_METHOD( Integer, Priority )
00371     {
00372       return thePriority;
00373     }
00374 
00375   
00376     SystemVectorCref getSystemVector() const
00377     {
00378       return theSystemVector;
00379     }
00380 
00381     /**
00382        Get the reference to the ProcessVector of this Stepper.
00383 
00384        The ProcessVector holds a set of pointers to this Stepper's Processes.
00385 
00386        The ProcessVector is partitioned in this way:
00387 
00388        |  Continuous Processes  |  Discrete Processes |
00389 
00390        getDiscreteProcessOffset() method returns the offset (index number)
00391        of the first discrete Process in this Stepper.
00392 
00393        Each part of the ProcessVector is sorted by Priority properties
00394        of Processes.
00395 
00396     */
00397 
00398     ProcessVectorCref getProcessVector() const
00399     {
00400       return theProcessVector;
00401     }
00402 
00403     /**
00404 
00405     @see getProcessVector()
00406 
00407     */
00408 
00409     const ProcessVector::size_type getDiscreteProcessOffset() const
00410     {
00411       return theDiscreteProcessOffset;
00412     }
00413 
00414     /**
00415        Get the reference to the VariableVector of this Stepper.
00416 
00417        In the VariableVector, Variables are classified and partitioned
00418        into the following three groups:
00419 
00420        | Write-Only Variables | Read-Write Variables | Read-Only Variables |
00421 
00422        Use getReadWriteVariableOffset() method to get the index of the first 
00423        Read-Write Variable in the VariableVector.  
00424 
00425        Use getReadOnlyVariableOffset() method to get the index of the first
00426        Read-Only Variable in the VariableVector.
00427        
00428 
00429     */
00430 
00431     VariableVectorCref getVariableVector() const
00432     {
00433       return theVariableVector;
00434     }
00435 
00436     /**
00437        @see getVariableVector()
00438     */
00439 
00440     const VariableVector::size_type getReadWriteVariableOffset() const
00441     {
00442       return theReadWriteVariableOffset;
00443     }
00444 
00445     /**
00446        @see getVariableVector()
00447     */
00448 
00449     const VariableVector::size_type getReadOnlyVariableOffset() const
00450     {
00451       return theReadOnlyVariableOffset;
00452     }
00453 
00454 
00455     RealVectorCref getValueBuffer() const
00456     {
00457       return theValueBuffer;
00458     }
00459 
00460 
00461     ECELL_API const VariableVector::size_type 
00462       getVariableIndex( VariableCptr const aVariable );
00463 
00464 
00465     virtual void interrupt( TimeParam aTime ) = 0;
00466 
00467     /**
00468         Definition of the Stepper dependency:
00469         Stepper A depends on Stepper B 
00470         if:
00471         - A and B share at least one Variable, AND
00472         - A reads AND B writes on (changes) the same Variable.
00473 
00474         See VariableReference class about the definitions of
00475         Variable 'read' and 'write'.
00476 
00477 
00478         @see Process, VariableReference
00479     */
00480 
00481     const bool isDependentOn( const StepperCptr aStepper );
00482 
00483     /** 
00484         This method updates theIntegratedVariableVector.
00485 
00486         theIntegratedVariableVector holds the Variables those
00487         isIntegrationNeeded() method return true.   
00488     
00489         This method must be called after initialize().
00490 
00491         @internal
00492      */
00493 
00494     void updateIntegratedVariableVector();
00495 
00496 
00497     virtual InterpolantPtr createInterpolant( VariablePtr aVariablePtr )
00498     {
00499       return new Interpolant( aVariablePtr );
00500     }
00501 
00502     const gsl_rng* getRng() const
00503     {
00504       return theRng;
00505     }
00506 
00507     bool operator<( StepperCref rhs )
00508     {
00509       return getCurrentTime() < rhs.getCurrentTime();
00510     }
00511 
00512     //    virtual StringLiteral getClassName() const  { return "Stepper"; }
00513 
00514 
00515   protected:
00516 
00517     ECELL_API void clearVariables();
00518 
00519     ECELL_API void fireProcesses();
00520 
00521     virtual void reset();
00522 
00523 
00524     /**
00525        Update theProcessVector.
00526 
00527     */
00528 
00529     void updateProcessVector();
00530 
00531 
00532     /**
00533        Update theVariableVector.
00534 
00535     */
00536 
00537     void updateVariableVector();
00538 
00539 
00540 
00541     /**
00542        Create Interpolant objects and distribute the objects to 
00543        write Variables.
00544 
00545        Ownership of the Interpolant objects are given away to the Variables.
00546 
00547        @see Variable::registerInterpolant()
00548     */
00549 
00550     void createInterpolants();
00551 
00552     /**
00553        Scan all the relevant Entity objects to this Stepper and construct
00554        the list of loggers.
00555 
00556        The list, theLoggerVector, is used in log() method.
00557 
00558     */
00559 
00560     void updateLoggerVector();
00561 
00562 
00563   protected:
00564 
00565     SystemVector        theSystemVector;
00566 
00567     LoggerVector  theLoggerVector;
00568 
00569     VariableVector            theVariableVector;
00570     VariableVector::size_type theReadWriteVariableOffset;
00571     VariableVector::size_type theReadOnlyVariableOffset;
00572 
00573     VariableVector            theIntegratedVariableVector;
00574 
00575     ProcessVector             theProcessVector;
00576     ProcessVector::size_type  theDiscreteProcessOffset;
00577 
00578     RealVector theValueBuffer;
00579 
00580 
00581 
00582   private:
00583 
00584     ModelPtr            theModel;
00585     
00586     // the index on the scheduler
00587     int                 theSchedulerIndex;
00588 
00589     Integer             thePriority;
00590 
00591     Real                theCurrentTime;
00592 
00593     Real                theStepInterval;
00594 
00595     Real                theMinStepInterval;
00596     Real                theMaxStepInterval;
00597 
00598     String              theID;
00599 
00600     gsl_rng*   theRng;
00601 
00602   };
00603 
00604 
00605 } // namespace libecs
00606 
00607 #endif /* __STEPPER_HPP */
00608 
00609 
00610 
00611 /*
00612   Do not modify
00613   $Author: sachiboo $
00614   $Revision: 2626 $
00615   $Date: 2006-11-24 13:39:27 +0100 (Fri, 24 Nov 2006) $
00616   $Locker$
00617 */

Generated on Fri Aug 31 18:32:07 2007 for E-CELL C++ libraries (libecs and libemc) 3.1.105 by  doxygen 1.5.3