       Re: Step functions

• To: mathgroup at smc.vnet.net
• Subject: [mg17063] Re: [mg17097] Step functions
• From: "Wolf, Hartmut" <hwolf at debis.com>
• Date: Fri, 23 Apr 1999 02:32:06 -0400
• Organization: debis Systemhaus
• References: <199904170735.DAA04892@smc.vnet.net.>
• Sender: owner-wri-mathgroup at wolfram.com

```Alessio Massaro schrieb:
>
> Can anyone help me to build a step function out of a series of {x,y} pairs?
>
> For ex.., consider an ordered random {x,y} series like
>
> data=Sort[Table[{Random[],Random[]}, {10}], First[#1]<First[#2]&]
>
> I would like to build a function f[ { {x1, y1}, {x2, y2}, ...}, x ], that
> evaluates to:
> - y[i]        if x=x[i]
> - y[i+1]    if x[i]<x<x[i+1]
> Here each point {xi, yi} determines f over the left-open interval
> x[i]<x<=x[i+1] of x.
> The right-open interval version would be:
> - y[i]        if x=x[i]
> - y[i]        if x[i]<x<x[i+1]
>

Dear Alessio

To the data {{x[i],y[i]}..} I'd like to add a point x such that the
function to be built is effectively defined as f[x]=y[i] if x[i-1] < x
<= x[i] for some i and undefined else.

So define

In:= n=10
In:= xValues=Sort[Table[Random[],{n+1}]]

In:= yValues=Table[Random[],{n}]

In:= data=Transpose[{xValues,Prepend[yValues,Undefined]}]
Out=
{{0.0431649,Undefined},{0.0616376,0.480382},{0.0723096,0.0116564},{0.159794,

0.382128},{0.207832,0.896267},{0.277301,0.922096},{0.404136,0.198678},

{0.527412,0.640826},{0.632598,0.862393},{0.739185,0.250286},{0.923058,
0.134352}}

In:=
makeStepsFun[defs:{{_,Undefined},{_,_}..}?OrderedQ, f_Symbol]:=
Module[{x},
f[x_]=Which[
Evaluate[Sequence@@Flatten[{x<=#[],#[]}& /@ defs]],
True,Undefined];]

In:= makeStepsFun[data,f]
In:= ?f
"Global`f"
f[x\$_] = Which[x\$ <= 0.04316494650005128, Undefined,
x\$ <= 0.06163756347928365, 0.4803820029119135, x\$ <=
0.07230960964988714,
0.01165635539654332, x\$ <= 0.1597935666518781, 0.3821282405189696,
x\$ <= 0.2078317731794699, 0.896266906762715, x\$ <=
0.2773005862054805,
0.9220959940925965, x\$ <= 0.4041356993425461, 0.1986775166791136,
x\$ <= 0.5274119538346457, 0.6408258258554689, x\$ <=
0.6325979692487199,
0.8623933751647133, x\$ <= 0.7391845993698257, 0.2502855634611418,
x\$ <= 0.923057985711199, 0.1343522133259901, True, Undefined]

In:= f/@ (data[] + {-10^-4,0,10^-4})
Out= {0.896267,0.896267,0.922096}

You can Plot this function:

In:= Plot[f[x],{x,First[data][],Last[data][]}]

But you can't Integrate it or take its Derivative!

To get a quality functional calculus you may use

In:= <<Calculus`DiracDelta`

In:= makeStepsFun[defs:{{_,Undefined},{_,_}..}?OrderedQ, f_Symbol]:=

Module[{x,xValues=Transpose[defs][],yValues=Rest[Transpose[defs][]]},
f[x_]=
(Append[yValues,0]-Prepend[yValues,0]).(UnitStep[x-#,ZeroValue->0]&
/@ xValues);
]

In:= makeStepsFun[data,f]
In:= ?f
"Global`f"
f[x\$_] = -0.1343522133259901*
UnitStep[-0.923057985711199 + x\$, ZeroValue -> 0] -
0.1159333501351517*UnitStep[-0.7391845993698257 + x\$, ZeroValue ->
0] -
0.6121078117035715*UnitStep[-0.6325979692487199 + x\$, ZeroValue ->
0] +
0.2215675493092443*UnitStep[-0.5274119538346457 + x\$, ZeroValue ->
0] +
0.4421483091763553*UnitStep[-0.4041356993425461 + x\$, ZeroValue ->
0] -
0.7234184774134828*UnitStep[-0.2773005862054805 + x\$, ZeroValue ->
0] +
0.02582908732988153*UnitStep[-0.2078317731794699 + x\$, ZeroValue ->
0] +
0.5141386662437453*UnitStep[-0.1597935666518781 + x\$, ZeroValue ->
0] +
0.3704718851224264*UnitStep[-0.07230960964988714 + x\$, ZeroValue ->
0] -
0.4687256475153702*UnitStep[-0.06163756347928365 + x\$, ZeroValue ->
0] +
0.4803820029119135*UnitStep[-0.04316494650005128 + x\$, ZeroValue ->
0]

In:= f/@ (data[] + {-10^-4,0,10^-4})
Out= {0.896267,0.896267,0.922096}

In:= Plot[f[x],{x,0,1}]

You can easily differentiate the function

In:= D[f[x],x]
Out= -0.134352 DiracDelta[-0.923058+x]-0.115933
DiracDelta[-0.739185+x]-0.612108
DiracDelta[-0.632598+x]+0.221568 DiracDelta[-0.527412+x]+0.442148
DiracDelta[-0.404136+x]-0.723418 DiracDelta[-0.277301+x]+0.0258291
DiracDelta[-0.207832+x]+0.514139 DiracDelta[-0.159794+x]+0.370472
DiracDelta[-0.0723096+x]-0.468726 DiracDelta[-0.0616376+x]+0.480382
DiracDelta[-0.0431649+x]

You can also integrate it. But obviously I just hit the complexity
barrier of Integrate for the sum of 11 UnitStep functions: Try

tt=(Integrate[Take[f[x],#],x]//Timing)& /@ Range

and then

tims=Map[Part[#,1,1]&, tt]

I found the values

{0.12,0.22,0.3,0.441,0.711,1.432,3.515,9.623,28.1,83.83,264.921}

<<Graphics`Graphics`

LogListPlot[tims,PlotJoined->True]

You'll see the exponential growth of the execution times. But if you
really need to integrate a steps function with many points, you can
construct the integral by yourself at ease according to the pattern
above.

In:= tt[]
Out= {0.32 Second,-0.134352 (-0.923058+x)
UnitStep[-0.923058+x,ZeroValue->0]-0.115933 (-0.739185+x)
UnitStep[-0.739185+x,ZeroValue->0]-0.612108 (-0.632598+x)
UnitStep[-0.632598+x,ZeroValue->0]}

Final remark: if you want the right open interval solution just change
the option ZeroValue->1 (which is the default), for the first method of
solution change <= to <

Kind regards
Hartmut Wolf

```

• References:
• Prev by Date: Re: Step functions
• Next by Date: Re: Infinite precision
• Previous by thread: Step functions
• Next by thread: Re: Step functions