Exemple #1
0
void FVMesh3D::complete_data()
{

// initialize the list of cell for each vertex    
for(size_t i=0;i<_nb_vertex;i++)
    {
    _vertex[i].nb_cell=0;
    }  
// we have to determine the list of neighbor cell for each vertex further
// compute the centroid and length of edge
for(size_t i=0;i<_nb_edge;i++)
    {
    _edge[i].centroid=(_edge[i].firstVertex->coord+_edge[i].secondVertex->coord)*(double)0.5;
    FVPoint3D<double> u;
    u=_edge[i].firstVertex->coord-_edge[i].secondVertex->coord;
    _edge[i].length=Norm(u);
    }
// We have completly finish with the edge

// compute geometric stuff for the face
for(size_t i=0;i<_nb_face;i++)
    {
    _face[i].perimeter=0.;
    _face[i].area=0.;
    _face[i].centroid=0.;
    // conpute  perimeter or the face 
    for(size_t j=0;j<_face[i].nb_edge;j++)
        {
        _face[i].perimeter+=_face[i].edge[j]->length; 
        _face[i].centroid+=_face[i].edge[j]->centroid*_face[i].edge[j]->length; 
        }
    // compute the centroid of the face
    _face[i].centroid/=_face[i].perimeter;  
    // compute the area of the face
    for(size_t j=0;j<_face[i].nb_edge;j++)
        {    
        FVPoint3D<double> u,v,w;  
        u=_face[i].edge[j]->firstVertex->coord-_face[i].centroid; 
        v=_face[i].edge[j]->secondVertex->coord-_face[i].centroid;
        w=CrossProduct(u,v);
        _face[i].area+=Norm(w)*0.5;
        }  
   // build the list of vertex pointer for the face  
    pos_v=0;
    for(size_t j=0;j<_face[i].nb_edge;j++)
        {
        bool _still_exist;   
        _still_exist=false; 
        for(size_t k=0;k<pos_v;k++)
             if(_face[i].edge[j]->firstVertex==_face[i].vertex[k])  _still_exist=true;
        if(!_still_exist) {_face[i].vertex[pos_v]=_face[i].edge[j]->firstVertex;pos_v++;}
        _still_exist=false;  
        for(size_t k=0;k<pos_v;k++)
             if(_face[i].edge[j]->secondVertex==_face[i].vertex[k])  _still_exist=true;
        if(!_still_exist) {_face[i].vertex[pos_v]=_face[i].edge[j]->secondVertex;pos_v++;}    
        }
    _face[i].nb_vertex=pos_v;         
    }
    //  left and right cell, normal vector will be determined after the loop on cells
// end loop on the faces  
for(size_t i=0;i<_nb_cell;i++)
    {
    _cell[i].surface=0.;
    _cell[i].volume=0.;
    _cell[i].centroid=0.;
    // conpute surface of the cell 
    // determine the left and right cell for the face
    for(size_t j=0;j<_cell[i].nb_face;j++)
        {
        size_t pos;    
        _cell[i].surface+=_cell[i].face[j]->area; 
        _cell[i].centroid+=_cell[i].face[j]->centroid*_cell[i].face[j]->area; 
        pos=_cell[i].face[j]->label-1;
        if(!(_face[pos].leftCell)  )  
             _face[pos].leftCell=&(_cell[i]);
        else
             _face[pos].rightCell=&(_cell[i]); 
        }
    // compute the centroid of the cell
    _cell[i].centroid/=_cell[i].surface;  
    // compute the cell2face vector
    // compute the volume of the cell
    for(size_t j=0;j<_cell[i].nb_face;j++)
        {
        _cell[i].cell2face[j]= _cell[i].face[j]->centroid-_cell[i].centroid;   
        for(size_t k=0;k<_cell[i].face[j]->nb_edge;k++)
            {
            FVPoint3D<double> u,v,w;
            u=_cell[i].cell2face[j];
            v=_cell[i].face[j]->edge[k]->firstVertex->coord-_cell[i].centroid;
            w=_cell[i].face[j]->edge[k]->secondVertex->coord-_cell[i].centroid;   
            _cell[i].volume+=fabs(Det(u,v,w))/6;
            }
        }   
    // build the list of the vertex pointer for a cell     
    pos_v=0;
    for(size_t j=0;j<_cell[i].nb_face;j++)
        for(size_t k=0;k<_cell[i].face[j]->nb_edge;k++)
            {
            bool _still_exist;   
            _still_exist=false;  
            for(size_t m=0;m<pos_v;m++)
                 if(_cell[i].face[j]->edge[k]->firstVertex==_cell[i].vertex[m])  _still_exist=true;
            if(!_still_exist) {_cell[i].vertex[pos_v]=_cell[i].face[j]->edge[k]->firstVertex;pos_v++;}
            _still_exist=false;  
            for(size_t m=0;m<pos_v;m++)
                 if(_cell[i].face[j]->edge[k]->secondVertex==_cell[i].vertex[m])  _still_exist=true;
            if(!_still_exist) {_cell[i].vertex[pos_v]=_cell[i].face[j]->edge[k]->secondVertex;pos_v++;}  
            }
     _cell[i].nb_vertex=pos_v;  
    // build the list of the cell pointer for a vertex        
     for(size_t j=0;j<_cell[i].nb_vertex;j++)
        {
        size_t pos;
        pos=_cell[i].vertex[j]->label-1;
        _vertex[pos].cell[_vertex[pos].nb_cell]=&(_cell[i]); 
        _vertex[pos].nb_cell++;
       if(_vertex[pos].nb_cell>=NB_CELL_PER_VERTEX_3D)
         cout<<"Warning, overflow in class FVVertex3D, too many Cells, found "<<_vertex[pos].nb_cell<<endl; 
        }
    }   
//  we compute the normal from left to rigth for each sub-triangle   
_boundary_face.resize(0);
_nb_boundary_face=0;
for(size_t i=0;i<_nb_face;i++)
    {
    for(size_t j=0;j<_face[i].nb_edge;j++)
        {
         FVPoint3D<double> u,v,w;  
         double no;
         u=_face[i].edge[j]->firstVertex->coord-_face[i].centroid;
         v=_face[i].edge[j]->secondVertex->coord-_face[i].centroid;       
         w=CrossProduct(u,v);
         no=Norm(w);
         w/=no;
         _face[i].normal[j]=w;
         u=_face[i].centroid-_face[i].leftCell->centroid;
         if(w*u<0) _face[i].normal[j]*=-1.; 
         }     // build the list of boundary face
    if(! (_face[i].rightCell)) {_boundary_face.push_back(&(_face[i]));_nb_boundary_face++;} 
    }
}
Exemple #2
0
  bool AdFront2 :: SameSide (const Point<2> & lp1, const Point<2> & lp2, 
                             const Array<int> * testfaces) const
  {
    int cnt = 0;

    if (testfaces)
      {
        for (int ii = 0; ii < testfaces->Size(); ii++)
          if (lines[(*testfaces)[ii]].Valid())
            {
              int i = (*testfaces)[ii];
              const Point<3> & p13d = points[lines[i].L().I1()].P();
              const Point<3> & p23d = points[lines[i].L().I2()].P();
              
              Point<2> p1(p13d(0), p13d(1));
              Point<2> p2(p23d(0), p23d(1));
              
              // p1 + alpha v = lp1 + beta vl
              Vec<2> v = p2-p1;
              Vec<2> vl = lp2 - lp1;
              Mat<2,2> mat, inv;
              Vec<2> rhs, sol;
              mat(0,0) = v(0);
              mat(1,0) = v(1);
              mat(0,1) = -vl(0);
              mat(1,1) = -vl(1);
              rhs = lp1-p1;
              
              if (Det(mat) == 0) continue;
              CalcInverse (mat, inv);
              sol = inv * rhs;
              if (sol(0) >= 0 && sol(0) <= 1 & sol(1) >= 0 && sol(1) <= 1)
                { cnt++; }
            }

      }
    else
      {
        for (int i = 0; i < lines.Size(); i++)
          if (lines[i].Valid())
            {
              const Point<3> & p13d = points[lines[i].L().I1()].P();
              const Point<3> & p23d = points[lines[i].L().I2()].P();
              
              Point<2> p1(p13d(0), p13d(1));
              Point<2> p2(p23d(0), p23d(1));
              
              // p1 + alpha v = lp1 + beta vl
              Vec<2> v = p2-p1;
              Vec<2> vl = lp2 - lp1;
              Mat<2,2> mat, inv;
              Vec<2> rhs, sol;
              mat(0,0) = v(0);
              mat(1,0) = v(1);
              mat(0,1) = -vl(0);
              mat(1,1) = -vl(1);
              rhs = lp1-p1;
              
              if (Det(mat) == 0) continue;
              CalcInverse (mat, inv);
              sol = inv * rhs;
              if (sol(0) >= 0 && sol(0) <= 1 & sol(1) >= 0 && sol(1) <= 1)
                { cnt++; }
            }
      }
    return ((cnt % 2) == 0);
  }
Exemple #3
0
// |M|
float Det(const Matrix3& m)
{
	return Det(m.mat);
}
Exemple #4
0
	void Matrix44f::invert( void )
	{
		float fDet =	_11*Det(	_22, _23, _24,
									_32, _33, _34,
									_42, _43, _44 ) -

						_12*Det(	_21, _23, _24,
									_31, _33, _34,
									_41, _43, _44 ) +

						_13*Det(	_21, _22, _24,
									_31, _32, _34,
									_41, _42, _44 ) -

						_14*Det(	_21, _22, _23,
									_31, _32, _33,
									_41, _42, _43 );

		// determinant must be not zero
		if( fabsf( fDet ) < 0.00001f )
			// error determinant is zero
			return;

		fDet = 1.0f / fDet;

		Matrix44f mMatrix;

		// Row1
		mMatrix._11 =		   Det(	_22, _23, _24,
									_32, _33, _34,
									_42, _43, _44 );

		mMatrix._12 = -1.0f * Det(	_21, _23, _24,
									_31, _33, _34,
									_41, _43, _44 );

		mMatrix._13 =		   Det(	_21, _22, _24,
									_31, _32, _34,
									_41, _42, _44 );

		mMatrix._14 = -1.0f * Det(	_21, _22, _23,
									_31, _32, _33,
									_41, _42, _43 );


		// Row2
		mMatrix._21 = -1.0f * Det(	_12, _13, _14,
									_32, _33, _34,
									_42, _43, _44 );

		mMatrix._22 =		   Det(	_11, _13, _14,
									_31, _33, _34,
									_41, _43, _44 );

		mMatrix._23 = -1.0f * Det(	_11, _12, _14,
									_31, _32, _34,
									_41, _42, _44 );

		mMatrix._24 =		   Det(	_11, _12, _13,
									_31, _32, _33,
									_41, _42, _43 );


		// Row3
		mMatrix._31 =		   Det(	_12, _13, _14,
									_22, _23, _24,
									_42, _43, _44 );

		mMatrix._32 = -1.0f * Det(	_11, _13, _14,
									_21, _23, _24,
									_41, _43, _44 );

		mMatrix._33 =		   Det(	_11, _12, _14,
									_21, _22, _24,
									_41, _42, _44 );

		mMatrix._34 = -1.0f * Det(	_11, _12, _13,
									_21, _22, _23,
									_41, _42, _43 );


		// Row4
		mMatrix._41 = -1.0f * Det(	_12, _13, _14,
									_22, _23, _24,
									_32, _33, _34 );

		mMatrix._42 =		   Det(	_11, _13, _14,
									_21, _23, _24,
									_31, _33, _34 );

		mMatrix._43 = -1.0f * Det(	_11, _12, _14,
									_21, _22, _24,
									_31, _32, _34 );

		mMatrix._44 =		   Det(	_11, _12, _13,
									_21, _22, _23,
									_31, _32, _33 );

		_11 = fDet*mMatrix._11;
		_12 = fDet*mMatrix._21;
		_13 = fDet*mMatrix._31;
		_14 = fDet*mMatrix._41;

		_21 = fDet*mMatrix._12;
		_22 = fDet*mMatrix._22;
		_23 = fDet*mMatrix._32;
		_24 = fDet*mMatrix._42;

		_31 = fDet*mMatrix._13;
		_32 = fDet*mMatrix._23;
		_33 = fDet*mMatrix._33;
		_34 = fDet*mMatrix._43;

		_41 = fDet*mMatrix._14;
		_42 = fDet*mMatrix._24;
		_43 = fDet*mMatrix._34;
		_44 = fDet*mMatrix._44;
	}
Exemple #5
0
void TestBandDiv(tmv::DivType dt)
{
    const int N = 10;

    std::vector<tmv::BandMatrixView<T> > b;
    std::vector<tmv::BandMatrixView<std::complex<T> > > cb;
    MakeBandList(b,cb);

    tmv::Matrix<T> a1(N,N);
    for (int i=0; i<N; ++i) for (int j=0; j<N; ++j) a1(i,j) = T(3+i-2*j);
    a1.diag().addToAll(T(10)*N);
    a1 /= T(10);

    tmv::Matrix<std::complex<T> > ca1 = a1 * std::complex<T>(3,-4);

    tmv::Vector<T> v1(N);
    tmv::Vector<T> v2(N-1);
    for (int i=0; i<N; ++i) v1(i) = T(16-3*i);
    for (int i=0; i<N-1; ++i) v2(i) = T(-6+i); 
    tmv::Vector<std::complex<T> > cv1(N);
    tmv::Vector<std::complex<T> > cv2(N-1);
    for (int i=0; i<N; ++i) cv1(i) = std::complex<T>(16-3*i,i+4); 
    for (int i=0; i<N-1; ++i) cv2(i) = std::complex<T>(2*i-3,-6+i); 

    tmv::Matrix<T> a3 = a1.colRange(0,N/2);
    tmv::Matrix<std::complex<T> > ca3 = ca1.colRange(0,N/2);
    tmv::Matrix<T> a4 = a1.rowRange(0,N/2);
    tmv::Matrix<std::complex<T> > ca4 = ca1.rowRange(0,N/2);
    tmv::Matrix<T> a5 = a1.colRange(0,0);
    tmv::Matrix<std::complex<T> > ca5 = ca1.colRange(0,0);
    tmv::Matrix<T> a6 = a1.rowRange(0,0);
    tmv::Matrix<std::complex<T> > ca6 = ca1.rowRange(0,0);
    tmv::Matrix<T> a7 = a1;
    tmv::Matrix<std::complex<T> > ca7 = ca1;
    a7.diag().addToAll(T(10)*N);
    ca7.diag().addToAll(T(10)*N);

    for(size_t i=START;i<b.size();i++) {
        if (showstartdone) 
            std::cout<<"Start loop: i = "<<i<<"\nbi = "<<tmv::TMV_Text(b[i])<<
                "  "<<b[i]<<std::endl;
        tmv::BandMatrixView<T> bi = b[i];
        tmv::BandMatrixView<std::complex<T> > cbi = cb[i];
        if (dt == tmv::LU && !bi.isSquare()) continue;

        bi.saveDiv();
        cbi.saveDiv();

        tmv::Matrix<T> m(bi);
        m.saveDiv();
        bi.divideUsing(dt);
        bi.setDiv();
        m.divideUsing(dt);
        m.setDiv();

        std::ostream* divout = showdiv ? &std::cout : 0;
        Assert(bi.checkDecomp(divout),"CheckDecomp");
        T eps = m.rowsize()*EPS*Norm(m)*Norm(m.inverse());

        if (bi.colsize() == N) {
            tmv::Vector<T> x1 = v1/bi;
            tmv::Vector<T> x2 = v1/m;
            if (showacc) {
                std::cout<<"v/b: Norm(x1-x2) = "<<Norm(x1-x2)<<
                    "  "<<eps*Norm(x1)<<std::endl;
            }
            Assert(Norm(x1-x2) < eps*Norm(x1),"Band v/b");
        }

        if (bi.rowsize() == N) {
            tmv::Vector<T> x1 = v1%bi;
            tmv::Vector<T> x2 = v1%m;
            if (showacc) {
                std::cout<<"v%b: Norm(x1-x2) = "<<Norm(x1-x2)<<
                    "  "<<eps*Norm(x1)<<std::endl;
            }
            Assert(Norm(x1-x2) < eps*Norm(x1),"Band v%b");
        }

        tmv::Matrix<T,tmv::ColMajor> binv = bi.inverse();
        tmv::Matrix<T,tmv::ColMajor> minv = m.inverse();
        if (showacc) {
            std::cout<<"minv = "<<minv<<std::endl;
            std::cout<<"binv = "<<binv<<std::endl;
            std::cout<<"Norm(minv-binv) = "<<Norm(minv-binv)<<
                "  "<<eps*Norm(binv)<<std::endl;
        }
        Assert(Norm(binv-minv) < eps*Norm(binv),"Band Inverse");

        if (m.isSquare()) {
            if (showacc) {
                std::cout<<"Det(b) = "<<Det(bi)<<
                    ", Det(m) = "<<Det(m)<<std::endl;
                std::cout<<"abs(bdet-mdet) = "<<std::abs(Det(bi)-Det(m));
                std::cout<<"  EPS*abs(mdet) = "<<
                    eps*std::abs(Det(m))<<std::endl;
                std::cout<<"abs(abs(bdet)-abs(mdet)) = "<<
                    std::abs(std::abs(Det(bi))-std::abs(Det(m)));
                std::cout<<"  EPS*abs(mdet) = "<<
                    eps*std::abs(Det(m))<<std::endl;
            }
            Assert(std::abs(Det(m)-Det(bi)) < eps*std::abs(Det(m)+Norm(m)),
                   "Band Det");
            T msign, bsign;
            Assert(std::abs(m.logDet(&msign)-bi.logDet(&bsign)) < N*eps,
                   "Band LogDet");
            Assert(std::abs(msign-bsign) < N*eps,"Band LogDet - sign");
        }

        cbi.divideUsing(dt);
        cbi.setDiv();
        Assert(cbi.checkDecomp(divout),"CheckDecomp");

        tmv::Matrix<std::complex<T> > cm(cbi);
        cm.saveDiv();
        cm.divideUsing(dt);
        cm.setDiv();
        T ceps = EPS*Norm(cm)*Norm(cm.inverse());

        if (cm.isSquare()) {
            if (showacc) {
                std::cout<<"Det(cbi) = "<<Det(cbi)<<", Det(cm) = "<<
                    Det(cm)<<std::endl;
                std::cout<<"abs(cbidet-cmdet) = "<<std::abs(Det(cbi)-Det(cm));
                std::cout<<"  cbidet/cmdet = "<<Det(cbi)/Det(cm);
                std::cout<<"  EPS*abs(cmdet) = "<<
                    ceps*std::abs(Det(cm))<<std::endl;
                std::cout<<"abs(abs(bdet)-abs(mdet)) = "<<
                    std::abs(std::abs(Det(bi))-std::abs(Det(m)));
                std::cout<<"  EPS*abs(mdet) = "<<
                    ceps*std::abs(Det(m))<<std::endl;
            }
            Assert(std::abs(Det(cbi)-Det(cm)) < 
                   ceps*std::abs(Det(cm)+Norm(cm)),
                   "Band CDet");
            std::complex<T> cmsign, cbsign;
            Assert(std::abs(cm.logDet(&cmsign)-cbi.logDet(&cbsign)) < N*eps,
                   "Band CLogDet");
            Assert(std::abs(cmsign-cbsign) < N*eps,"Band CLogDet - sign");
        }

        tmv::Vector<std::complex<T> > cv(v1 * std::complex<T>(1,1));
        cv(1) += std::complex<T>(-1,5);
        cv(2) -= std::complex<T>(-1,5);

        if (m.colsize() == N) {
            // test real / complex
            tmv::Vector<std::complex<T> > y1 = v1/cbi;
            tmv::Vector<std::complex<T> > y2 = v1/cm;
            if (showacc) {
                std::cout<<"v/cb: Norm(y1-y2) = "<<Norm(y1-y2)<<
                    "  "<<ceps*Norm(y1)<<std::endl;
            }
            Assert(Norm(y1-y2) < ceps*Norm(y1),"Band v/cb");

            // test complex / real
            y1 = cv/bi;
            y2 = cv/m;
            if (showacc) {
                std::cout<<"cv/b: Norm(y1-y2) = "<<Norm(y1-y2)<<
                    "  "<<eps*Norm(y1)<<std::endl;
            }
            Assert(Norm(y1-y2) < eps*Norm(y1),"Band cv/b");

            // test complex / complex
            y1 = cv/cbi;
            y2 = cv/cm;
            if (showacc) {
                std::cout<<"cv/cb: Norm(y1-y2) = "<<Norm(y1-y2)<<
                    "  "<<ceps*Norm(y1)<<std::endl;
            }
            Assert(Norm(y1-y2) < ceps*Norm(y1),"Band cv/cb");
        }

        if (bi.rowsize() == N) {
            tmv::Vector<std::complex<T> > y1 = v1%cbi;
            tmv::Vector<std::complex<T> > y2 = v1%cm;
            if (showacc) {
                std::cout<<"v%cb: Norm(y1-y2) = "<<Norm(y1-y2)<<
                    "  "<<ceps*Norm(y1)<<std::endl;
            }
            Assert(Norm(y1-y2) < ceps*Norm(y1),"Band v%cb");

            y1 = cv%bi;
            y2 = cv%m;
            if (showacc) {
                std::cout<<"cv%b: Norm(y1-y2) = "<<Norm(y1-y2)<<
                    "  "<<eps*Norm(y1)<<std::endl;
            }
            Assert(Norm(y1-y2) < eps*Norm(y1),"Band cv%b");
            y1 = cv%cbi;
            y2 = cv%cm;
            if (showacc) {
                std::cout<<"cv%cb: Norm(y1-y2) = "<<Norm(y1-y2)<<
                    "  "<<ceps*Norm(y1)<<std::endl;
            }
            Assert(Norm(y1-y2) < ceps*Norm(y1),"Band cv%cb");
        }

    }

    TestBandDiv_A<T>(dt);
    TestBandDiv_B1<T>(dt);
    TestBandDiv_B2<T>(dt);
    TestBandDiv_C1<T>(dt);
    if (dt == tmv::LU) TestBandDiv_C2<T>(dt);
    TestBandDiv_D1<T>(dt);
    if (dt == tmv::LU) TestBandDiv_D2<T>(dt);

    std::cout<<"BandMatrix<"<<tmv::TMV_Text(T())<<"> Division using ";
    std::cout<<tmv::TMV_Text(dt)<<" passed all tests\n";
}
Exemple #6
0
bool link_det_minor(
	size_t                     size     , 
	size_t                     repeat   , 
	CppAD::vector<double>     &matrix   ,
	CppAD::vector<double>     &gradient )
{
	// -----------------------------------------------------
	// setup

	// object for computing determinant
	typedef CppAD::AD<double>       ADScalar; 
	typedef CppAD::vector<ADScalar> ADVector; 
	CppAD::det_by_minor<ADScalar>   Det(size);

	size_t i;               // temporary index
	size_t m = 1;           // number of dependent variables
	size_t n = size * size; // number of independent variables
	ADVector   A(n);        // AD domain space vector
	ADVector   detA(m);     // AD range space vector
	
	// vectors of reverse mode weights 
	CppAD::vector<double> w(1);
	w[0] = 1.;

	// the AD function object
	CppAD::ADFun<double> f;

	static bool printed = false;
	bool print_this_time = (! printed) & (repeat > 1) & (size >= 3);

	extern bool global_retape;
	if( global_retape ) while(repeat--)
	{
		// choose a matrix
		CppAD::uniform_01(n, matrix);
		for( i = 0; i < size * size; i++)
			A[i] = matrix[i];
	
		// declare independent variables
		Independent(A);
	
		// AD computation of the determinant
		detA[0] = Det(A);
	
		// create function object f : A -> detA
		f.Dependent(A, detA);

		extern bool global_optimize;
		if( global_optimize )
		{	size_t before, after;
			before = f.size_var();
			f.optimize();
			if( print_this_time ) 
			{	after = f.size_var();
				std::cout << "cppad_det_minor_optimize_size_" 
				          << int(size) << " = [ " << int(before) 
				          << ", " << int(after) << "]" << std::endl;
				printed         = true;
				print_this_time = false;
			}
		}
	
		// get the next matrix
		CppAD::uniform_01(n, matrix);
	
		// evaluate the determinant at the new matrix value
		f.Forward(0, matrix);
	
		// evaluate and return gradient using reverse mode
		gradient = f.Reverse(1, w);
	}
	else
	{
		// choose a matrix
		CppAD::uniform_01(n, matrix);
		for( i = 0; i < size * size; i++)
			A[i] = matrix[i];
	
		// declare independent variables
		Independent(A);
	
		// AD computation of the determinant
		detA[0] = Det(A);
	
		// create function object f : A -> detA
		CppAD::ADFun<double> f;
		f.Dependent(A, detA);

		extern bool global_optimize;
		if( global_optimize )
		{	size_t before, after;
			before = f.size_var();
			f.optimize();
			if( print_this_time ) 
			{	after = f.size_var();
				std::cout << "optimize: size = " << size
				          << ": size_var() = "
				          << before << "(before) " 
				          << after << "(after) " 
				          << std::endl;
				printed         = true;
				print_this_time = false;
			}
		}
	
		// ------------------------------------------------------
		while(repeat--)
		{	// get the next matrix
			CppAD::uniform_01(n, matrix);
	
			// evaluate the determinant at the new matrix value
			f.Forward(0, matrix);
	
			// evaluate and return gradient using reverse mode
			gradient = f.Reverse(1, w);
		}
	}
	return true;
}
Exemple #7
0
bool link_det_minor(
	size_t                     size     ,
	size_t                     repeat   ,
	CppAD::vector<double>     &matrix   ,
	CppAD::vector<double>     &gradient )
{
	// speed test global option values
	if( global_option["atomic"] )
		return false;

	// -----------------------------------------------------
	// setup

	// object for computing determinant
	typedef CppAD::AD<double>       ADScalar;
	typedef CppAD::vector<ADScalar> ADVector;
	CppAD::det_by_minor<ADScalar>   Det(size);

	size_t i;               // temporary index
	size_t m = 1;           // number of dependent variables
	size_t n = size * size; // number of independent variables
	ADVector   A(n);        // AD domain space vector
	ADVector   detA(m);     // AD range space vector

	// vectors of reverse mode weights
	CppAD::vector<double> w(1);
	w[0] = 1.;

	// the AD function object
	CppAD::ADFun<double> f;

	// ---------------------------------------------------------------------
	if( ! global_option["onetape"] ) while(repeat--)
	{
		// choose a matrix
		CppAD::uniform_01(n, matrix);
		for( i = 0; i < size * size; i++)
			A[i] = matrix[i];

		// declare independent variables
		Independent(A);

		// AD computation of the determinant
		detA[0] = Det(A);

		// create function object f : A -> detA
		f.Dependent(A, detA);

		if( global_option["optimize"] )
			f.optimize();

		// skip comparison operators
		f.compare_change_count(0);

		// evaluate the determinant at the new matrix value
		f.Forward(0, matrix);

		// evaluate and return gradient using reverse mode
		gradient = f.Reverse(1, w);
	}
	else
	{
		// choose a matrix
		CppAD::uniform_01(n, matrix);
		for( i = 0; i < size * size; i++)
			A[i] = matrix[i];

		// declare independent variables
		Independent(A);

		// AD computation of the determinant
		detA[0] = Det(A);

		// create function object f : A -> detA
		f.Dependent(A, detA);

		if( global_option["optimize"] )
			f.optimize();

		// skip comparison operators
		f.compare_change_count(0);

		// ------------------------------------------------------
		while(repeat--)
		{	// get the next matrix
			CppAD::uniform_01(n, matrix);

			// evaluate the determinant at the new matrix value
			f.Forward(0, matrix);

			// evaluate and return gradient using reverse mode
			gradient = f.Reverse(1, w);
		}
	}
	return true;
}