constraints.cpp
Go to the documentation of this file.
00001 #include <kdl/constraints.hpp>
00002 #include <kdl/jacobianframe.hpp>
00003 #include <fstream>
00004 #include <iomanip>
00005 
00006 using namespace KDL;
00007 
00012 ConstraintMatrix::ConstraintMatrix(int _maxrows,int _maxcols) :
00013       maxrows(_maxrows),
00014       maxcols(_maxcols),
00015       cmat(new double[_maxrows*_maxcols]),
00016       cmatstride(_maxcols),
00017       desval(new double[_maxrows]),
00018       weight(new double[_maxrows]),   /* square root of the constraint weight matrix */
00019       jsweight(new double[_maxcols]), /* square root of the joint space weight matrix */
00020       pinvtmps( _maxrows>_maxcols?_maxrows:_maxcols), 
00021       /*pinvtmps(
00022         _maxrows>_maxcols?_maxrows:_maxcols, 
00023         _maxrows>_maxcols?_maxrows:_maxcols,
00024         100,
00025         5E-2), */
00026       cmati(new double[_maxrows*_maxcols]),
00027       cmatistride(_maxrows),
00028       nrOfConstraints(0),      
00029       eps(0.05),
00030       nrofits(100)
00031     {}
00032 
00033   void ConstraintMatrix::dump(std::ostream& os) {
00034       int p = os.precision(7);
00035           int w = 16;
00036           std::ios_base::fmtflags fl = os.setf(std::ios::scientific);
00037       int i,j;
00038       os << "Constraint Matrix and desired velocity(last column)" << std::endl;
00039       for (i=0;i<nrOfConstraints;++i) {
00040           for (j=0;j<nrofjoints;++j) {
00041               os << std::setw(w) << cmat[i*cmatstride+j] << "\t";
00042           }
00043           os << desval[i];
00044           os << std::endl;
00045       }
00046       os.flags(fl);
00047           os.precision(p);
00048   }
00049 
00050   void ConstraintMatrix::dumpsvd(std::ostream& os) {
00051       int p = os.precision(7);
00052           int w = 16;
00053           std::ios_base::fmtflags fl = os.setf(std::ios::scientific);
00054       int i;
00055       for (i=0;i<nrofjoints;++i) {
00056           os << std::setw(w) << pinvtmps.S[pinvtmps.ndx[i]] << " ";
00057       }
00058       os << std::endl;
00059       os.flags(fl);
00060           os.precision(p);
00061   }
00062 
00063         void ConstraintMatrix::resetConstraints(int _nrofjoints) {
00064         int i;
00065         nrofjoints = _nrofjoints;
00066         nrOfConstraints=0;        
00067         for (i=0;i<nrofjoints;++i) {
00068             jsweight[i]=1.0;
00069         }
00070     }
00071     void ConstraintMatrix::addConstraint(const Jacobian<double>& c,double K,double _desval,double _desvald,double _weight) {
00072         int i;        
00073         assert((0<=nrOfConstraints)&&(nrOfConstraints<maxrows));
00074         assert((!c.hasDerivs())||(c.nrOfDeriv()==nrofjoints));
00075         desval[nrOfConstraints] = K*(_desval - c.value()) + _desvald;
00076         weight[nrOfConstraints] = ::sqrt(_weight);
00077         if (c.hasDerivs()) {
00078             for (i=0;i<nrofjoints;++i) {
00079                                 if (c.hasDeriv(i)) {
00080                                         cmat[cmatstride*nrOfConstraints+i] = c.deriv(i);
00081                                 } else {
00082                                         cmat[cmatstride*nrOfConstraints+i] = 0.0;
00083                                 }
00084                         }
00085         } else {
00086             for (i=0;i<nrofjoints;++i) {
00087                 cmat[cmatstride*nrOfConstraints+i] = 0.0;
00088             }
00089         }
00090         nrOfConstraints++;
00091     }
00092 
00093     void ConstraintMatrix::addConstraintJoint(int jointnr,double value,double K,double _desval,double _desvald,double _weight) {
00094         int i;        
00095         assert((0<=nrOfConstraints)&&(nrOfConstraints<maxrows));
00096         desval[nrOfConstraints] = K*(_desval - value) + _desvald;
00097         weight[nrOfConstraints] = ::sqrt(_weight);
00098         for (i=0;i<nrofjoints;++i) {
00099             cmat[cmatstride*nrOfConstraints+i] = (i==jointnr)?1.0:0.0;
00100         }
00101         nrOfConstraints++;
00102     }
00103 
00104 
00105         void ConstraintMatrix::addConstraint(
00106                 const Jacobian<Vector>& c,
00107                 double K,
00108                 const Vector& _desval,
00109                 const Vector& _desvald,
00110                 double _weight
00111         ) {
00112         assert((0<=nrOfConstraints)&&(nrOfConstraints+2<maxrows));
00113         assert((!c.hasDerivs())||(c.nrOfDeriv()==nrofjoints));
00114                 int r,i;
00115                 Vector d = K*(_desval- c.value()) + _desvald;
00116         _weight = ::sqrt(_weight);
00117                 for (r=0;r<3;r++) {     
00118                         desval[nrOfConstraints] = d(r);
00119                         weight[nrOfConstraints] = _weight;
00120                         if (c.hasDerivs()) {
00121                                 for (i=0;i<nrofjoints;++i) {
00122                                         if (c.hasDeriv(i)) {
00123                                                 cmat[cmatstride*nrOfConstraints+i] = c.deriv(i)(r);
00124                                         } else {
00125                                                 cmat[cmatstride*nrOfConstraints+i] = 0.0;
00126                                         }
00127                                 }
00128                         } else {
00129                                 for (i=0;i<nrofjoints;++i) {
00130                                         cmat[cmatstride*nrOfConstraints+i] = 0.0;
00131                                 }
00132                         }
00133                         nrOfConstraints++;
00134                 }        
00135         }
00139         void ConstraintMatrix::addConstraint(
00140                 const Jacobian<Frame>& c,
00141                 const std::vector<double>& K,
00142                 const Frame& _desval,
00143                 const Twist& _desvald,
00144                 const std::vector<double>& _weight
00145         ) {
00146         assert((0<=nrOfConstraints)&&(nrOfConstraints+5<maxrows));
00147         assert((!c.hasDerivs())||(c.nrOfDeriv()==nrofjoints));
00148                 int r,i;
00149                 Twist d = diff(c.value(),_desval,1.0);
00150                 for (r=0;r<6;r++) {     
00151                         desval[nrOfConstraints] = K[r]*d(r)+_desvald(r);
00152                         weight[nrOfConstraints] = ::sqrt(_weight[r]);
00153                         if (c.hasDerivs()) {
00154                                 for (i=0;i<nrofjoints;++i) {
00155                                         if (c.hasDeriv(i)) {
00156                                                 cmat[cmatstride*nrOfConstraints+i] = c.deriv(i)(r);
00157                                         } else {
00158                                                 cmat[cmatstride*nrOfConstraints+i] = 0.0;
00159                                         }
00160                                 }
00161                         } else {
00162                                 for (i=0;i<nrofjoints;++i) {
00163                                         cmat[cmatstride*nrOfConstraints+i] = 0.0;
00164                                 }
00165                         }
00166                         nrOfConstraints++;
00167                 }        
00168     }
00169 
00173         void ConstraintMatrix::addConstraintWithoutControl(
00174                 const Jacobian<Frame>& c,
00175                 const Twist& desired,
00176                 const std::vector<double>& _weight
00177         ) {
00178         assert((0<=nrOfConstraints)&&(nrOfConstraints+5<maxrows));
00179         assert((!c.hasDerivs())||(c.nrOfDeriv()==nrofjoints));
00180                 int r,i;
00181                 for (r=0;r<6;r++) {     
00182                         desval[nrOfConstraints] = desired(r);
00183                         weight[nrOfConstraints] = ::sqrt(_weight[r]);
00184                         if (c.hasDerivs()) {
00185                                 for (i=0;i<nrofjoints;++i) {
00186                                         if (c.hasDeriv(i)) {
00187                                                 cmat[cmatstride*nrOfConstraints+i] = c.deriv(i)(r);
00188                                         } else {
00189                                                 cmat[cmatstride*nrOfConstraints+i] = 0.0;
00190                                         }
00191                                 }
00192                         } else {
00193                                 for (i=0;i<nrofjoints;++i) {
00194                                         cmat[cmatstride*nrOfConstraints+i] = 0.0;
00195                                 }
00196                         }
00197                         nrOfConstraints++;
00198                 }   
00199     }
00200 
00201 
00202 
00203         void ConstraintMatrix::addConstraint(
00204                 const Jacobian<Frame>& c,
00205                 double Kpos,
00206                 double Krot,
00207                 const Frame& _desval,
00208                 const Twist& _desvald,
00209                 double _weightpos,
00210                 double _weightrot
00211         ) {
00212         assert((0<=nrOfConstraints)&&(nrOfConstraints+5<maxrows));
00213         assert((!c.hasDerivs())||(c.nrOfDeriv()==nrofjoints));
00214                 int r,i;
00215                 Twist d = diff(c.value(),_desval,1.0);
00216         _weightpos = ::sqrt(_weightpos);
00217         _weightrot = ::sqrt(_weightrot);
00218                 for (r=0;r<6;r++) {     
00219                         if (r<3) {
00220                                 desval[nrOfConstraints] = Kpos*d(r)+_desvald(r);
00221                                 weight[nrOfConstraints] = _weightpos;
00222                         } else {
00223                                 desval[nrOfConstraints] = Krot*d(r)+_desvald(r);
00224                                 weight[nrOfConstraints] = _weightrot;
00225                         }
00226                         if (c.hasDerivs()) {
00227                                 for (i=0;i<nrofjoints;++i) {
00228                                         if (c.hasDeriv(i)) {
00229                                                 cmat[cmatstride*nrOfConstraints+i] = c.deriv(i)(r);
00230                                         } else {
00231                                                 cmat[cmatstride*nrOfConstraints+i] = 0.0;
00232                                         }
00233                                 }
00234                         } else {
00235                                 for (i=0;i<nrofjoints;++i) {
00236                                         cmat[cmatstride*nrOfConstraints+i] = 0.0;
00237                                 }
00238                         }
00239                         nrOfConstraints++;
00240                 }        
00241         }
00242 
00243 
00244 
00245         void ConstraintMatrix::addConstraint(
00246                 const Jacobian<Twist>& c,
00247                 double Kpos,
00248                 double Krot,
00249                 const Twist& _desval,
00250                 const Twist& _desvald,
00251                 double _weightpos,
00252                 double _weightrot
00253         ) {
00254         assert((0<=nrOfConstraints)&&(nrOfConstraints+5<maxrows));
00255         assert((!c.hasDerivs())||(c.nrOfDeriv()==nrofjoints));
00256                 int r,i;
00257                 Twist d = _desval - c.value();
00258         _weightpos = ::sqrt(_weightpos);
00259         _weightrot = ::sqrt(_weightrot);
00260                 for (r=0;r<6;r++) {     
00261                         if (r<3) {
00262                                 desval[nrOfConstraints] = Kpos*d(r)+_desvald(r);
00263                                 weight[nrOfConstraints] = _weightpos;
00264                         } else {
00265                                 desval[nrOfConstraints] = Krot*d(r)+_desvald(r);
00266                                 weight[nrOfConstraints] = _weightrot;
00267                         }
00268                         if (c.hasDerivs()) {
00269                                 for (i=0;i<nrofjoints;++i) {
00270                                         if (c.hasDeriv(i)) {
00271                                                 cmat[cmatstride*nrOfConstraints+i] = c.deriv(i)(r);
00272                                         } else {
00273                                                 cmat[cmatstride*nrOfConstraints+i] = 0.0;
00274                                         }
00275                                 }
00276                         } else {
00277                                 for (i=0;i<nrofjoints;++i) {
00278                                         cmat[cmatstride*nrOfConstraints+i] = 0.0;
00279                                 }
00280                         }
00281                         nrOfConstraints++;
00282                 }        
00283         }
00284 
00285 
00286 
00287 
00288         void ConstraintMatrix::addConstraint(
00289                 const Jacobian<Wrench>& c,
00290                 double Kpos,
00291                 double Krot,
00292                 const Wrench& _desval,
00293                 const Wrench& _desvald,
00294                 double _weightpos,
00295                 double _weightrot
00296         ) {
00297 
00298         assert((0<=nrOfConstraints)&&(nrOfConstraints+5<maxrows));
00299         assert((!c.hasDerivs())||(c.nrOfDeriv()==nrofjoints));
00300                 int r,i;
00301         _weightpos = ::sqrt(_weightpos);
00302         _weightrot = ::sqrt(_weightrot);
00303                 Wrench d = diff(c.value(),_desval,1.0);
00304                 for (r=0;r<6;r++) {     
00305                         if (r<3) {
00306                                 desval[nrOfConstraints] = Kpos*d(r)+_desvald(r);
00307                                 weight[nrOfConstraints] = _weightpos;
00308                         } else {
00309                                 desval[nrOfConstraints] = Krot*d(r)+_desvald(r);
00310                                 weight[nrOfConstraints] = _weightrot;
00311                         }
00312                         if (c.hasDerivs()) {
00313                                 for (i=0;i<nrofjoints;++i) {
00314                                         if (c.hasDeriv(i)) {
00315                                                 cmat[cmatstride*nrOfConstraints+i] = c.deriv(i)(r);
00316                                         } else {
00317                                                 cmat[cmatstride*nrOfConstraints+i] = 0.0;
00318                                         }
00319                                 }
00320                         } else {
00321                                 for (i=0;i<nrofjoints;++i) {
00322                                         cmat[cmatstride*nrOfConstraints+i] = 0.0;
00323                                 }
00324                         }
00325                         nrOfConstraints++;
00326                 }        
00327         }
00334     void ConstraintMatrix::calculateOutput(std::vector<double>& output) {
00335         int i;
00336         if (nrOfConstraints==0) {
00337             for (i=0;i<nrofjoints;++i) output[i]=0.0;
00338             return;
00339         }
00340         /*
00341         int i,j;
00342         double sum;
00343         // temporary implementation..
00344         //MatrixOutput(std::cout,cmat,cmatstride,maxrows,maxcols);
00345         //std::cout << std::endl;
00346         pinvtmps.pinv(cmat,cmatstride,nrOfConstraints,maxcols,cmati,cmatistride);
00347         //MatrixOutput(std::cout,cmati,cmatistride,maxcols,maxrows);
00348         // std::cout << std::endl;
00349         for (i=0;i<maxcols;++i) {
00350             sum = 0.0;
00351             for (j=0;j<nrOfConstraints;++j) {
00352                 sum+= cmati[ cmatistride* i + j]  * desval[j];
00353             }
00354             output[i] = sum;
00355         }*/
00356                 /*
00357         if (lowerprior) {
00358             lowerprior->calculateOutput(output2);
00359             pinvtmps.inverseWithNullSpace(
00360                 cmat,cmatstride,nrOfConstraints,maxcols,
00361                 desval, output2,
00362                 weight,jsweight,
00363                 output);
00364         } else {
00365                 */
00366         /*pinvtmps.inverse(
00367             cmat,cmatstride,nrOfConstraints,nrofjoints,
00368             desval,
00369             weight,jsweight,
00370             output);*/
00371         pinvtmps.prepare(cmat,cmatstride,nrOfConstraints,nrofjoints,weight,jsweight,nrofits);
00372                 // WARNING : this makes some assumptions on the implementation of vector<double> :
00373         pinvtmps.inverse(desval,&output[0],eps);
00374     }
00375 
00376     ConstraintMatrix::~ConstraintMatrix() {
00377         delete [] cmat;
00378         delete [] desval;
00379         delete [] weight;
00380                 delete [] jsweight;
00381         delete [] cmati;
00382     }
00383 
00384         void ConstraintMatrix::setJointSpaceWeights(const std::vector<double>& jsw) {
00385                 int i;
00386                 for (i=0;i<nrofjoints;++i) {
00387             jsweight[i]=::sqrt(jsw[i]);
00388         }
00389         }
00394         void ConstraintMatrix::calculateOutput(std::vector<double>& output,const std::vector<double>& nullspace) {
00395         int i;
00396         if (nrOfConstraints==0) {
00397             for (i=0;i<nrofjoints;++i) output[i]=nullspace[i];
00398             return;
00399         }
00400         
00401         /*pinvtmps.inverseWithNullSpace(
00402             cmat,cmatstride,nrOfConstraints,nrofjoints,
00403             desval,nullspace,
00404             weight,jsweight,
00405             output);*/
00406         
00407         pinvtmps.prepare(cmat,cmatstride,nrOfConstraints,nrofjoints,weight,jsweight,nrofits);
00408         pinvtmps.inverseWithNullSpace(desval,&output[0],&nullspace[0],eps); 
00409         //dumpsvd(std::cout);
00410     }
00411 
00412 
00413     void ConstraintMatrix::reduce(const std::vector<bool>& list,const std::vector<double> value) {
00414         int newcol =0;   // index in the reduced vector (newcol <= col)
00415         for (int col=0;col<nrofjoints;++col) {
00416             // PRE COND : 0..col-1 is reduced
00417            int row;
00418            if (!list[col]) {
00419                 // if not fixed
00420                 // adapt col :
00421                 for (row=0;row<nrOfConstraints;++row)
00422                     cmat[cmatstride*row+newcol] = cmat[cmatstride*row+col];
00423                 // adapt joint space weights :
00424                 jsweight[newcol]=jsweight[col];
00425                 // adapt desired values and indices.
00426                 newcol++;
00427            } else {
00428                for (row=0;row<nrOfConstraints;++row) {
00429                    desval[row] -= cmat[cmatstride*row+col]*value[row]; 
00430                }
00431            }
00432            // POST COND 0..col is reduced into a vector of 0..newcol-1
00433         }
00434         // reduce nrofjoints
00435         nrofjoints= newcol;
00436     }
00437 
00438     void ConstraintMatrix::reducejv(const std::vector<bool>& list,std::vector<double>& vec)
00439         {
00440         int newcol =0;
00441         for (int col=0;col<nrofjoints;++col) {
00442            if (!list[col]) {
00443                 vec[newcol] = vec[col];
00444                 newcol++;
00445            }
00446         }
00447     }
00448 
00449     void ConstraintMatrix::expandjv(int nrofalljoints,const std::vector<bool>& list,const std::vector<double>& values,std::vector<double>& vec)
00450     {
00451         int oldcol =nrofjoints-1;
00452         for (int col=nrofalljoints-1;col>=0;--col) {
00453            // PRE : vec is expanded for col+1<i<nrofalljoints
00454            if (!list[col]) {
00455                 vec[col] = vec[oldcol];
00456                 oldcol--;
00457            } else {
00458                 vec[col] = values[col];
00459            }
00460            // POST : vec is expanded for col<i<nrofalljoints
00461         }
00462     }
00463 
00464 
00465 
00466     void ConstraintMatrix::calculateOutput(const std::vector<bool>& list, const std::vector<double>& value, std::vector<double>& output) {
00467         int nrofalljoints = nrofjoints;
00468         reduce(list,value);
00469         calculateOutput(output);  
00470         expandjv(nrofalljoints,list,value,output);
00471     }
00472 
00473 
00474     void ConstraintMatrix::calculateOutput(
00475                 const std::vector<bool>& list, 
00476                 const std::vector<double>& values, 
00477                 std::vector<double>& output,
00478                 std::vector<double>& nullspace) 
00479         {
00480         int nrofalljoints = nrofjoints;
00481         reduce(list,values);
00482         reducejv(list,nullspace);
00483         calculateOutput(output,nullspace);
00484         expandjv(nrofalljoints,list,values,output);
00485     }
00486 
00487 


orocos_kdl
Author(s): Ruben Smits, Erwin Aertbelien, Orocos Developers
autogenerated on Sat Dec 28 2013 17:17:25