Re: Problems with differentiating Piecewise functions

*To*: mathgroup at smc.vnet.net*Subject*: [mg87111] Re: Problems with differentiating Piecewise functions*From*: hlovatt <howard.lovatt at gmail.com>*Date*: Tue, 1 Apr 2008 03:21:18 -0500 (EST)*References*: <200803260955.EAA09634@smc.vnet.net> <fsg6r6$j9q$1@smc.vnet.net>

On Mar 29, 8:30 pm, Andrzej Kozlowski <a... at mimuw.edu.pl> wrote: > On 28 Mar 2008, at 12:26, Andrzej Kozlowski wrote: > > > > > > > On 28 Mar 2008, at 09:16, hlovatt wrote: > >> On Mar 28, 12:18 am, Andrzej Kozlowski <a... at mimuw.edu.pl> wrote: > >>> On 26 Mar 2008, at 10:55, hlovatt wrote: > > >>>> If I set up a piecewise function and differentiate it: > > >>>> In[112]:= pw1 = Piecewise[{{x^2, x <= 0}, {x, x > 0}}] > > >>>> Out[112]= \[Piecewise] { > >>>> {x^2, x <= 0}, > >>>> {x, x > 0} > >>>> } > > >>>> In[113]:= pw1 /. x -> 0 > > >>>> Out[113]= 0 > > >>>> In[114]:= pw1d = D[pw1, x] > > >>>> Out[114]= \[Piecewise] { > >>>> {2 x, x < 0}, > >>>> {1, x > 0}, > >>>> {Indeterminate, \!\(\* > >>>> TagBox["True", > >>>> "PiecewiseDefault", > >>>> AutoDelete->False, > >>>> DeletionWarning->True]\)} > >>>> } > > >>>> In[115]:= pw1d /. x -> 0 > > >>>> Out[115]= Indeterminate > > >>>> Then at the joins between the pieces I get Indeterminate values, > >>>> because the limit x <= 0 has become x < 0 after differentiation. > >>>> Does > >>>> anyone know a solution to this problem? > > >>>> Thanks, > > >>>> Howard. > > >>> What do you mean by "a solution to this problem"? You have a > >>> function that is not differentiable at 0 and you would like it's > >>> derivative to have a value there? You can't expect a "solution to a > >>> problem" when you do not tell us what is the problem (except the > >>> fact > >>> that not all functions are differentiable - but that's life). > >>> Note that is your pieceise function is actually differentiable than > >>> the derivative is defined everywhere: > > >>> pw2 = Piecewise[{{x^2, x <= 0}, {x^3, x > 0}}]; > > >>> pw2d = D[pw2, x] > >>> Piecewise[{{2*x, x < 0}, {0, x == 0}}, 3*x^2] > > >>> This is also as it should be. What else would you expect? > > >>> Andrzej Kozlowski > > >> Thanks to everyone who replied. I have to apologise for the bad > >> example that I posted (I simplified my problem by cutting and pasting > >> an example from the help file to keep the post short). I am actually > >> fitting cubic splines and the functions are continuous up to the > >> second derivative (at least to the accuracy of machine precision). A > >> better example is: > > >> In[54]:= pw[x_] := > >> Piecewise[{{0.+ 0.007508378277320685 x + 7.561460342471517*10^-7 x^3, > >> x < 50}, {-4.8729206849430454*10^-6 (-125.76959597633721 + > >> x) (1148.1044516606876- 47.50636365246156 x + x^2), 50 <= x}}] > > >> In[55]:= pw[x] > > >> Out[55]= \[Piecewise] { > >> {0.+ 0.00750838 x + 7.56146*10^-7 x^3, x < 50}, > >> {-4.87292*10^-6 (-125.77 + x) (1148.1- 47.5064 x + x^2), 50 <= x} > >> } > > >> In[56]:= pw[50] > > >> Out[56]= 0.469937 > > >> In[57]:= pw[50 + 10^-30] > > >> Out[57]= 0.469937 > > >> In[58]:= pw[50 - 10^-30] > > >> Out[58]= 0.469937 > > >> In[60]:= pw'[x] > > >> Out[60]= \[Piecewise] { > >> {0.00750838+ 2.26844*10^-6 x^2, x < 50}, > >> {-4.87292*10^-6 (-125.77 + x) (-47.5064 + 2 x) - > >> 4.87292*10^-6 (1148.1- 47.5064 x + x^2), x > 50}, > >> {Indeterminate, \!\(\* > >> TagBox["True", > >> "PiecewiseDefault", > >> AutoDelete->False, > >> DeletionWarning->True]\)} > >> } > > >> In[61]:= pw'[50] > > >> Out[61]= Indeterminate > > >> In[62]:= pw'[50 + 10^-30] > > >> Out[62]= 0.0131795 > > >> In[63]:= pw'[50 - 10^-30] > > >> Out[63]= 0.0131795 > > >> Also if you Plot pw or pw' you get an annoying gap in the plot at the > >> join (but strangely not pw''). My guess is that Mathematica is too > >> pedantic about machine precision and is treating each piece as an > >> algebraic equation. However this does not explain why Plot behaves > >> funnily and doesn't help if you are trying to do numerical analysis. > > > You are violating one of the most fundamental principles of computer > > algebra: do not mix approximate numbers with symbolic computation. > > More correctly, such "mixing" requires a great deal of care and > > symbolic algebraic techniques that can deal with approximate numbers > > (and even more so with machine precision input) are still in their > > infancy. (In fact Mathematica is one of the few systems that make it > > to some extent possible). In your case the symbolic technique you > > are using is differentiation of a piecewise function, and this > > cannot be reliably combined with numerical precision input. > > > The answer to your problem is simple. Switch from using a mixture of > > symbolic methods and approximate input to a purely numeric setting. > > The best way to do this, I think, is by using FunctionInterpolation. > > So what you need to do is this: > > > pw[x_] := > > Piecewise[{{0. + 0.007508378277320685 x + 7.561460342471517*10^-7 x^3, > > x < 50}, {-4.8729206849430454*10^-6 (-125.76959597633721 + > > x) (1148.1044516606876 - 47.50636365246156 x + x^2), 50 <= x}}] > > > f = FunctionInterpolation[pw[x], {x, 0, 80}]; > > > Plot[f[x], {x, 40, 60}] > > > shows a continuous curve > > > Plot[f'[x], {x, 40, 60}] > > > shows an almost smooth curve, with a slight "kink" at the break > > point. One could probably play with the options to > > FunctionInterpolation to "smoothen" it. > > > Andrzej Kozlowski > > Actually, you can get a smooth looking derivative by using a higher > interpolation order: > > f = FunctionInterpolation[pw[x], {x, 0, 80}, InterpolationOrder -> 10]; > > Plot[f'[x], {x, 40, 60}] > > looks very smooth and so does: > > Plot[f''[x], {x, 40, 60}] > > Andrzej Kozlowski Thanks for the advice. I was aware that I could use FunctionInterpolation but I actually wanted to plot my splines not an approximation to them. I guess I am asking too much since Piecewise takes algebraic expressions, unlike FunctionInterpolation, and therefore must evaluate symbolically.