vtf-logo

shells/applications/cylinderElastic/excentric/ExBasicSensor.h

Go to the documentation of this file.
00001 // -*- C++ -*-
00002 //
00003 // ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
00004 // 
00005 //                                   Fehmi Cirak
00006 //                        California Institute of Technology
00007 //                           (C) 2004 All Rights Reserved
00008 //
00009 // <LicenseText>
00010 //
00011 // ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
00012 //
00013 #ifndef EXBASICSENSOR_H
00014 #define EXBASICSENSOR_H
00015 #include <functional>
00016 #include <iterator>
00017 #include <cmath>
00018 
00019 #include "shells/driverCC/MShell.h"
00020 #include "shells/driverCC/SVertexFunctors.h"
00021 
00022 
00023 
00024 namespace cylExp {
00025     template<typename EXTR>
00026     class BasicSensor;
00027 }
00028 
00029 
00030 namespace cylExp {
00031     
00032     template<typename EXTR>
00033     class BasicSensor {
00034     public:
00035         BasicSensor(std::ostream& os, shells::MShell * const mShell, 
00036                     const double sensorPosition[shells::SVertexCoordinate::numVar]);
00037         ~BasicSensor(){_os.flush();}
00038         
00039         void printData(double timeStamp);
00040     
00041     private:
00042         BasicSensor(const BasicSensor &);
00043         const BasicSensor & operator=(const BasicSensor &);
00044         
00045     private:
00046         typedef std::vector<typename EXTR::DataType>                 _DataCont;
00047         typedef std::vector<shells::SVertexCoordinate::DataType>     _CoordinateCont;
00048         
00049 
00050         static const unsigned                    _spaceDim;     
00051         std::ostream&                           _os;
00052         shells::MShell                  * const _mShell;
00053         int                                     _closestVertexID;
00054         shells::SVertexCoordinate::DataType     _position[shells::SVertexCoordinate::numVar];
00055     };
00056 }
00057 
00058 
00059 // implementations
00060 namespace cylExp {
00061     
00062     // definition of static variable
00063     template<typename EXTR>
00064     const unsigned BasicSensor<EXTR>::_spaceDim = shells::SVertexCoordinate::numVar;
00065 
00066     
00067     // implementation of member methods
00068     template<typename EXTR>
00069     BasicSensor<EXTR>::BasicSensor(std::ostream& os, shells::MShell * const mShell, 
00070                                    const double sensorPosition[shells::SVertexCoordinate::numVar]):
00071         _os(os), _mShell(mShell)
00072     {
00073         // scientific format for output
00074         _os << std::scientific;
00075 
00076         // collect all the reference coordinates
00077         _CoordinateCont coordinates;
00078         size_t numVertices = _mShell->numberOfVertices();
00079         coordinates.reserve(numVertices*_spaceDim);
00080         
00081         
00082         shells::SVertexCollector<std::back_insert_iterator<_CoordinateCont>, 
00083             shells::SVertexCoordinate> getCoordinates;
00084         _mShell->iterateOverVertices(std::bind2nd(getCoordinates, 
00085                                                   std::back_inserter(coordinates)));
00086         
00087         assert((numVertices*_spaceDim)==coordinates.size());
00088         assert(numVertices);
00089         
00090         // find the closest vertex ID to sensorPosition
00091         double minDistanceSqr = 0.0;
00092         _closestVertexID = 0;
00093         
00094         for (unsigned j=0; j<_spaceDim; ++j) { 
00095             minDistanceSqr += (sensorPosition[j]-coordinates[j])*
00096                 (sensorPosition[j]-coordinates[j]);
00097         }
00098                 
00099         // find the closest vertex 
00100         for (unsigned i=1; i<numVertices; ++i) {
00101             double distanceSqr = 0.0;
00102             for (unsigned j=0; j<_spaceDim; ++j) {
00103                 distanceSqr += (sensorPosition[j]-coordinates[i*_spaceDim+j])*
00104                     (sensorPosition[j]-coordinates[i*_spaceDim+j]); 
00105             }
00106             
00107             if (distanceSqr<minDistanceSqr) {
00108                 minDistanceSqr = distanceSqr;
00109                 _closestVertexID = i;
00110             }
00111         }
00112         
00113         for (unsigned i=0; i<_spaceDim; ++i) {
00114             _position[i] = coordinates[_closestVertexID*_spaceDim+i];
00115         }
00116         
00117         std::cout << "Attaching to vertex with GlobalD: " << _closestVertexID << " and position ";
00118         for (unsigned i=0; i<_spaceDim; ++i) {
00119             std::cout << _position[i] << " ";
00120         }
00121         std::cout << std::endl;
00122     }
00123 
00124 
00125     
00126     template<typename EXTR>
00127     void BasicSensor<EXTR>::printData(double timeStamp) 
00128     {
00129         const size_t numVar = EXTR::numVar;
00130         size_t numVertices = _mShell->numberOfVertices();
00131         
00132         // apply EXTR to all vertices for collecting data
00133         _DataCont variable;     
00134         variable.reserve(numVertices*numVar);
00135         shells::SVertexCollector<std::back_insert_iterator<_DataCont>, EXTR> getData;
00136         _mShell->iterateOverVertices(std::bind2nd(getData, 
00137                                                   std::back_inserter(variable)));       
00138         
00139         assert((numVertices*numVar)==variable.size());
00140         
00141         // print the data belonging to _closestVertexID
00142         double disp[3];
00143         _os << timeStamp << " ";
00144 
00145         for (unsigned i=0; i<numVar; ++i) {
00146             unsigned offSet = _closestVertexID*numVar+i;
00147             assert(offSet<variable.size());
00148             disp[i] = variable[offSet];
00149             _os << disp[i] << " ";
00150         }       
00151         
00152         double rad = std::sqrt(disp[0]*disp[0]+disp[1]*disp[1]);
00153         const double skp = disp[0]*_position[0]+disp[1]*_position[1];
00154         
00155         if (skp<0.0) {
00156             rad = -rad;
00157         }
00158 
00159         _os << rad << std::endl;
00160     }
00161 }
00162 
00163 #endif

Generated on Fri Aug 24 13:00:24 2007 for SFC Thin-Shell Finite Element Solver by  doxygen 1.4.7