PLearn 0.1
SoftSlopeIntegralVariable.cc
Go to the documentation of this file.
00001 // -*- C++ -*-
00002 
00003 // PLearn (A C++ Machine Learning Library)
00004 // Copyright (C) 1998 Pascal Vincent
00005 // Copyright (C) 1999-2002 Pascal Vincent, Yoshua Bengio, Rejean Ducharme and University of Montreal
00006 // Copyright (C) 2001-2002 Nicolas Chapados, Ichiro Takeuchi, Jean-Sebastien Senecal
00007 // Copyright (C) 2002 Xiangdong Wang, Christian Dorion
00008 
00009 // Redistribution and use in source and binary forms, with or without
00010 // modification, are permitted provided that the following conditions are met:
00011 // 
00012 //  1. Redistributions of source code must retain the above copyright
00013 //     notice, this list of conditions and the following disclaimer.
00014 // 
00015 //  2. Redistributions in binary form must reproduce the above copyright
00016 //     notice, this list of conditions and the following disclaimer in the
00017 //     documentation and/or other materials provided with the distribution.
00018 // 
00019 //  3. The name of the authors may not be used to endorse or promote
00020 //     products derived from this software without specific prior written
00021 //     permission.
00022 // 
00023 // THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR
00024 // IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
00025 // OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN
00026 // NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
00027 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
00028 // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
00029 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
00030 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
00031 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
00032 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00033 // 
00034 // This file is part of the PLearn library. For more information on the PLearn
00035 // library, go to the PLearn Web site at www.plearn.org
00036 
00037 
00038 /* *******************************************************      
00039  * $Id: SoftSlopeIntegralVariable.cc 4204 2005-10-07 19:51:47Z tihocan $
00040  * This file is part of the PLearn library.
00041  ******************************************************* */
00042 
00043 #include "SoftSlopeIntegralVariable.h"
00044 #include "Var_utils.h"
00045 
00046 namespace PLearn {
00047 using namespace std;
00048 
00049 
00053 PLEARN_IMPLEMENT_OBJECT(SoftSlopeIntegralVariable, 
00054                         "This Var computes the integral of the soft_slope function in an interval.", 
00055                         "Compute the integral of soft_slope(x,s,l,r) over x from a to b\n");
00056 
00057 SoftSlopeIntegralVariable::SoftSlopeIntegralVariable()
00058     : a(0), b(0), tabulated(false)
00059 { }
00060   
00061 SoftSlopeIntegralVariable::  SoftSlopeIntegralVariable(Variable* smoothness, Variable* left, Variable* right, real a_, real b_, bool tabulated_)
00062     : inherited(VarArray(smoothness) & Var(left) & Var(right), 
00063                 smoothness->length()<left->length()?left->length():smoothness->length(), 
00064                 smoothness->width()<left->width()?left->width():smoothness->width()),
00065       a(a_), b(b_), tabulated(tabulated_)
00066 {}
00067 
00068 void
00069 SoftSlopeIntegralVariable::declareOptions(OptionList &ol)
00070 {
00071     declareOption(ol, "a", &SoftSlopeIntegralVariable::a, OptionBase::buildoption, "");
00072     declareOption(ol, "b", &SoftSlopeIntegralVariable::b, OptionBase::buildoption, "");
00073     declareOption(ol, "tabulated", &SoftSlopeIntegralVariable::tabulated, OptionBase::buildoption, "");
00074     inherited::declareOptions(ol);
00075 }
00076 
00077 void SoftSlopeIntegralVariable::recomputeSize(int& l, int& w) const
00078 { 
00079     l=0; 
00080     w=0;
00081     if (varray.size() && varray[0] && varray[1] && varray[2]) {
00082         for (int i = 0; i < 3; i++) {
00083             if (varray[i]->length() > l)
00084                 l = varray[i]->length();
00085             if (varray[i]->width() > w)
00086                 w = varray[i]->width();
00087         }
00088         for (int i = 0; i < 3; i++) {
00089             if (varray[i]->length() != l || varray[i]->width() != w) {
00090                 if (varray[i]->length() != 1 || varray[i]->width() != 1)
00091                     PLERROR("Each argument of SoftSlopeIntegralVariable should either have the same length/width as the others or length 1");
00092             }
00093         }
00094     }
00095 }
00096 
00097 
00098 void SoftSlopeIntegralVariable::fprop()
00099 {
00100     int n=nelems();
00101     int n1=varray[0]->nelems();
00102     int n2=varray[1]->nelems();
00103     int n3=varray[2]->nelems();
00104     real* smoothness = varray[0]->valuedata;
00105     real* left = varray[1]->valuedata;
00106     real* right = varray[2]->valuedata;
00107 
00108     if (n1==n && n2==n && n3==n)
00109         for(int i=0; i<n; i++)
00110             valuedata[i] = tabulated?tabulated_soft_slope_integral(smoothness[i], left[i], right[i],a,b):soft_slope_integral(smoothness[i], left[i], right[i],a,b);
00111     else if (n1==1 && n2==n && n3==n)
00112         for(int i=0; i<n; i++)
00113             valuedata[i] = tabulated?tabulated_soft_slope_integral(*smoothness, left[i], right[i],a,b):soft_slope_integral(*smoothness, left[i], right[i],a,b);
00114     else
00115     {
00116         int m1= n1==1?0:1;
00117         int m2= n2==1?0:1;
00118         int m3= n3==1?0:1;
00119         for(int i=0; i<n; i++,smoothness+=m1,left+=m2,right+=m3)
00120             valuedata[i] = tabulated?tabulated_soft_slope_integral(*smoothness, *left, *right, a, b):soft_slope_integral(*smoothness, *left, *right, a, b);
00121     }
00122 }
00123 
00124 
00125 void SoftSlopeIntegralVariable::bprop()
00126 {
00127     int n=nelems();
00128     int n1=varray[0]->nelems();
00129     int n2=varray[1]->nelems();
00130     int n3=varray[2]->nelems();
00131     int m1= n1==1?0:1;
00132     int m2= n2==1?0:1;
00133     int m3= n3==1?0:1;
00134     real* smoothness = varray[0]->valuedata;
00135     real* left = varray[1]->valuedata;
00136     real* right = varray[2]->valuedata;
00137     real* dsmoothness = varray[0]->gradientdata;
00138     real* dleft = varray[1]->gradientdata;
00139     real* dright = varray[2]->gradientdata;
00140     for(int i=0; i<n; i++,smoothness+=m1,left+=m2,right+=m3,dsmoothness+=m1,dleft+=m2,dright+=m3)
00141     {
00142         if (fast_exact_is_equal(*smoothness, 0)) continue;
00143         // soft_slope_integral =
00144         // (b - a) + (softplus_primitive(-smoothness*(b-right)) - softplus_primitive(-smoothness*(b-left))
00145         //    -softplus_primitive(-smoothness*(a-right)) + softplus_primitive(-smoothness*(a-left)))/
00146         //     (smoothness*smoothness*(right-left));
00147         // hence 
00148         //
00149         //  d/dsmoothness = (softplus(-smoothness*(b-right))*(right-b) + softplus(-smoothness*(b-left))*(b-left)
00150         //                 + softplus(-smoothness*(a-right))*(a-right) + softplus(-smoothness*(a-left))*(left-a))/
00151         //     (smoothness*smoothness*(right-left))
00152         //     - 2 * (soft_slope_integral - b + a) / smoothness
00153         //n
00154         //  d/dleft = (-softplus(-smoothness*(b-left)) + softplus(-smoothness*(a-left)))/
00155         //     (smoothness*(right-left))
00156         //     + (soft_slope_integral - b + a)/ (right-left)
00157         //
00158         //  d/dright =  (softplus(-smoothness*(b-right)) - softplus(-smoothness*(a-right)))/(smoothness*(right-left))
00159         //         - (soft_slope_integral - b + a)/ (right-left)
00160         //
00161         real inv_smoothness = 1.0 / *smoothness;
00162         real br = (b-*right);
00163         real bl = (b-*left);
00164         real ar = (a-*right);
00165         real al = (a-*left);
00166         real t1 = tabulated?tabulated_softplus(- *smoothness*br):softplus(- *smoothness*br);
00167         real t2 = tabulated?tabulated_softplus(- *smoothness*bl):softplus(- *smoothness*bl);
00168         real t3 = tabulated?tabulated_softplus(- *smoothness*ar):softplus(- *smoothness*ar);
00169         real t4 = tabulated?tabulated_softplus(- *smoothness*al):softplus(- *smoothness*al);
00170         real inv_delta=1.0/(*right-*left);
00171         real ssiab = valuedata[i]-b+a;
00172         *dsmoothness += gradientdata[i] * 
00173             ((-t1*br + t2*bl + t3*ar - t4*al)*inv_smoothness*inv_delta - 2*ssiab)*inv_smoothness;
00174         *dleft += gradientdata[i] * ((-t2 + t4)*inv_smoothness + ssiab) * inv_delta;
00175         *dright += gradientdata[i] * ((t1 - t3)*inv_smoothness - ssiab) * inv_delta;
00176     }
00177 }
00178 
00179 void SoftSlopeIntegralVariable::symbolicBprop()
00180 {
00181     PLERROR("SoftSlopeIntegralVariable::symbolicBprop() not implemented");
00182 }
00183 
00184 
00185 
00186 } // end of namespace PLearn
00187 
00188 
00189 /*
00190   Local Variables:
00191   mode:c++
00192   c-basic-offset:4
00193   c-file-style:"stroustrup"
00194   c-file-offsets:((innamespace . 0)(inline-open . 0))
00195   indent-tabs-mode:nil
00196   fill-column:79
00197   End:
00198 */
00199 // vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:encoding=utf-8:textwidth=79 :
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines