00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
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(
Variable* smoothness,
Variable* left,
Variable* right,
real a_,
real b_,
bool tabulated_)
00058 :
inherited(
VarArray(smoothness) &
Var(
left) &
Var(
right),
00059 smoothness->length()<
left->length()?
left->length():smoothness->length(),
00060 smoothness->width()<
left->width()?
left->width():smoothness->width()),
00061 a(a_), b(b_), tabulated(tabulated_)
00062 {}
00063
00064
void
00065 SoftSlopeIntegralVariable::declareOptions(
OptionList &ol)
00066 {
00067
declareOption(ol,
"a", &SoftSlopeIntegralVariable::a, OptionBase::buildoption,
"");
00068
declareOption(ol,
"b", &SoftSlopeIntegralVariable::b, OptionBase::buildoption,
"");
00069
declareOption(ol,
"tabulated", &SoftSlopeIntegralVariable::tabulated, OptionBase::buildoption,
"");
00070 inherited::declareOptions(ol);
00071 }
00072
00073 void SoftSlopeIntegralVariable::recomputeSize(
int& l,
int& w)
const
00074
{
00075 l=0;
00076 w=0;
00077
if (varray.
size() && varray[0] && varray[1] && varray[2]) {
00078
for (
int i = 0; i < 3; i++) {
00079
if (varray[i]->length() > l)
00080 l = varray[i]->length();
00081
if (varray[i]->width() > w)
00082 w = varray[i]->width();
00083 }
00084
for (
int i = 0; i < 3; i++) {
00085
if (varray[i]->length() != l || varray[i]->width() != w) {
00086
if (varray[i]->length() != 1 || varray[i]->width() != 1)
00087
PLERROR(
"Each argument of SoftSlopeIntegralVariable should either have the same length/width as the others or length 1");
00088 }
00089 }
00090 }
00091 }
00092
00093
00094 void SoftSlopeIntegralVariable::fprop()
00095 {
00096
int n=
nelems();
00097
int n1=varray[0]->
nelems();
00098
int n2=varray[1]->nelems();
00099
int n3=varray[2]->nelems();
00100
real* smoothness = varray[0]->valuedata;
00101
real*
left = varray[1]->valuedata;
00102
real*
right = varray[2]->valuedata;
00103
00104
if (n1==n && n2==n && n3==n)
00105
for(
int i=0; i<n; i++)
00106 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);
00107
else if (n1==1 && n2==n && n3==n)
00108
for(
int i=0; i<n; i++)
00109 valuedata[i] =
tabulated?
tabulated_soft_slope_integral(*smoothness,
left[i],
right[i],
a,
b):
soft_slope_integral(*smoothness,
left[i],
right[i],
a,
b);
00110
else
00111 {
00112
int m1= n1==1?0:1;
00113
int m2= n2==1?0:1;
00114
int m3= n3==1?0:1;
00115
for(
int i=0; i<n; i++,smoothness+=m1,
left+=m2,
right+=m3)
00116 valuedata[i] =
tabulated?
tabulated_soft_slope_integral(*smoothness, *
left, *
right,
a,
b):
soft_slope_integral(*smoothness, *
left, *
right,
a,
b);
00117 }
00118 }
00119
00120
00121 void SoftSlopeIntegralVariable::bprop()
00122 {
00123
int n=
nelems();
00124
int n1=varray[0]->
nelems();
00125
int n2=varray[1]->nelems();
00126
int n3=varray[2]->nelems();
00127
int m1= n1==1?0:1;
00128
int m2= n2==1?0:1;
00129
int m3= n3==1?0:1;
00130
real* smoothness = varray[0]->valuedata;
00131
real*
left = varray[1]->valuedata;
00132
real*
right = varray[2]->valuedata;
00133
real* dsmoothness = varray[0]->gradientdata;
00134
real* dleft = varray[1]->gradientdata;
00135
real* dright = varray[2]->gradientdata;
00136
for(
int i=0; i<n; i++,smoothness+=m1,
left+=m2,
right+=m3,dsmoothness+=m1,dleft+=m2,dright+=m3)
00137 {
00138
if (*smoothness == 0)
continue;
00139
00140
00141
00142
00143
00144
00145
00146
00147
00148
00149
00150
00151
00152
00153
00154
00155
00156
00157
real inv_smoothness = 1.0 / *smoothness;
00158
real br = (
b-*
right);
00159
real bl = (
b-*
left);
00160
real ar = (
a-*
right);
00161
real al = (
a-*
left);
00162
real t1 =
tabulated?
tabulated_softplus(- *smoothness*br):
softplus(- *smoothness*br);
00163
real t2 =
tabulated?
tabulated_softplus(- *smoothness*bl):
softplus(- *smoothness*bl);
00164
real t3 =
tabulated?
tabulated_softplus(- *smoothness*ar):
softplus(- *smoothness*ar);
00165
real t4 =
tabulated?
tabulated_softplus(- *smoothness*al):
softplus(- *smoothness*al);
00166
real inv_delta=1.0/(*
right-*
left);
00167
real ssiab = valuedata[i]-
b+
a;
00168 *dsmoothness += gradientdata[i] *
00169 ((-t1*br + t2*bl + t3*ar - t4*al)*inv_smoothness*inv_delta - 2*ssiab)*inv_smoothness;
00170 *dleft += gradientdata[i] * ((-t2 + t4)*inv_smoothness + ssiab) * inv_delta;
00171 *dright += gradientdata[i] * ((t1 - t3)*inv_smoothness - ssiab) * inv_delta;
00172 }
00173 }
00174
00175 void SoftSlopeIntegralVariable::symbolicBprop()
00176 {
00177
PLERROR(
"SoftSlopeIntegralVariable::symbolicBprop() not implemented");
00178 }
00179
00180
00181
00182 }
00183
00184