[ADOL-C] tapeless adol-c question

Ian Washington washinid at mcmaster.ca
Wed May 21 14:06:09 EDT 2014


Thanks kshitij,

The only location where I dynamically allocate adtl::adouble is in the
function 'ad_evaluate' given as,

void ad_evaluate
( int n, int m, int numdirs, double *xinit,
  double **Seed_J, double ***Jc_ret )
{
   adtl::adouble *x = new adtl::adouble[n];
   adtl::adouble *y = new adtl::adouble[m];

   for (int i=0; i<n; i++) x[i] = xinit[i];

   for (int i=0; i<n;++i) {
     x[i].setADValue(Seed_J[i]);
   }

   ceval_ad_tl(n, x, m, y); <-- evaluate functions

   double **Jc = myalloc2(m, numdirs);

   for (int i=0; i<m; i++){
     for (int j=0; j<numdirs; j++)
       Jc[i][j] = y[i].getADValue(j);
   }

   *Jc_ret = Jc;

   delete[] x; <-- KILLED HERE
   delete[] y; <-- KILLED HERE
}

Note that I delete these adtl::adouble's after coping the Jacobian.

Also there are many array definitions of adtl::adouble in the function
'ceval_ad_tl' :

void ceval_ad_tl(int n, adtl::adouble *x, int m, adtl::adouble *c)
{
  adtl::adouble cA[nde][nel][3];
  adtl::adouble cB[nde][nel][3];
  adtl::adouble cAdot[nde][nel][3];
  adtl::adouble cBdot[nde][nel][3];

  adtl::adouble q1,qde,qfe,qex,time;
  adtl::adouble q2,q3,q4,qra;

  adtl::adouble sum;

 ...

}

Do you think these definitions are the problem? Should I change these
arrays to be dynamically allocated, so that they can be deleted? What
about the scalar variables?

Thanks,
Ian.




On 05/21/2014 01:13 PM, Kshitij Kulshreshtha wrote:
> Hello,
> 
> So this warning is produced only in the case when some objects of type
> adtl::adouble still exist in memory after the function computation with
> them has finished. These exisiting objects already have some memory
> allocated to them and if setNumDir() tries to increase the number of
> directions, these objects will still have the old memory and cannot
> store all the directions.
> 
> The way out of this is to make absolutely certain that all adtl::adouble
> objects have been deallocated before you call setNumDir(). Then they
> must be allocated again for the next function computation.
> 
> Also you don't require the #define ADOLC_TAPELESS anymore since you're
> using both traced and traceless versions in their respective namespaces.
> 
> Regards
> Kshitij.
> 
> As on 2014-05-20 23:21h, Ian Washington did write:
>> Hello all,
>>
>> I am new to the tapeless version of adol-c and I have a question related
>> to setting the number of directional derivatives (numdirs) when using
>> the forward vector mode.
>>
>> In essence I would like to reset numdirs for a number of possibly
>> different Jacobian matrices.
>>
>> For example, consider the following 'pseudo' code:
>>
>> #define ADOLC_TAPELESS
>> #include <adolc/adolc.h>
>> #include <adolc/adolc_sparse.h>
>> #include <adolc/adtl.h>
>> #include <ColPack/ColPackHeaders.h>
>>
>> int main() {
>>
>>   // n = indep.
>>   // m = dep.
>>   // xinit = initial point
>>   // gGraph = colpack via 'BipartiteGraphPartialColoringInterface'
>>   // Seed_J = seed
>>   // Jac_P = jac. pattern using 'jac_pat'
>>   // nnz = nonzeros
>>   // numdirs = directions
>>
>>   // preprocess to get Seed and Jac. pattern
>>
>>   ad_preprocess(n, m, xinit, &gGraph, &Seed_J, &Jac_P, &nnz, &numdirs);
>>
>>   // note, ad_preprocess uses the tape-based adolc to get Jac_P, Seed_J
>>
>>   // set numdirs (must be called before adtl::adouble definitions)
>>
>>   adtl::setNumDir(numdirs);
>>
>>   // evaluate to get compressed Jac.
>>
>>   ad_evaluate(n, m, numdirs, xinit, Seed_J, &Jc);
>>
>>   // re-set everything and get a possibly new Jac.
>>
>>   adtl::setNumDir(numdirs_n);  <--- PROBLEM HERE
>>
>>   ad_evaluate(n_n, m_n, numdirs_n, xinit_n, Seed_J_n, &Jc_n);
>>
>>   return 0;
>> }
>>
>> where the 'ad_evaluate' function is:
>>
>> void ad_evaluate
>> ( int n, int m, int numdirs, double *xinit,
>>   double **Seed_J, double ***Jc_ret )
>> {
>>
>>   adtl::adouble *x = new adtl::adouble[n];
>>   adtl::adouble *y = new adtl::adouble[m];
>>
>>   for (int i=0; i<n; i++) x[i] = xinit[i];
>>
>>   for (int i=0; i<n;++i) {
>>     x[i].setADValue(Seed_J[i]);
>>   }
>>
>>   ceval_ad_tl(n, x, m, y); <-- evaluate functions
>>
>>   double **Jc = myalloc2(m, numdirs);
>>
>>   for (int i=0; i<m; i++){
>>     for (int j=0; j<numdirs; j++)
>>       Jc[i][j] = y[i].getADValue(j);
>>   }
>>
>>   *Jc_ret = Jc;
>>
>>   delete[] x;
>>   delete[] y;
>> }
>>
>>
>> The problem with the above is when I reset numdirs using
>> adtl::setNumDir(numdirs_n) the second time I get the following:
>>
>> ADOL-C Warning: Tapeless: Setting numDir will not change the number of
>> directional derivative in existing adoubles and may lead to erronious
>> results or memory corruption
>>
>> Note, if I just remove the second adtl::setNumDir(numdirs_n) and
>> evaluate the same Jacobian everything works fine.
>>
>> So my question is how do I compute two different Jacobian matrices in
>> the same program, which have a different Seed and number of directional
>> derivatives?
>>
>> Thanks,
>> Ian.
>>
>>
>>
>>
>>
>> _______________________________________________
>> ADOL-C mailing list
>> ADOL-C at list.coin-or.org
>> http://list.coin-or.org/mailman/listinfo/adol-c
>>
> 



More information about the ADOL-C mailing list