Implemented step function transformation
This commit is contained in:
parent
3e04d3390d
commit
0328b86833
|
@ -2,7 +2,7 @@
|
||||||
let timeDist =
|
let timeDist =
|
||||||
GenericDistribution.make(
|
GenericDistribution.make(
|
||||||
~generationSource=
|
~generationSource=
|
||||||
GuesstimatorString("mm(floor(normal(30,3)), normal(39,1), [.5,.5])"),
|
GuesstimatorString("mm(floor(normal(30,2)), normal(39,1), [.5,.5])"),
|
||||||
~probabilityType=Pdf,
|
~probabilityType=Pdf,
|
||||||
~domain=Complete,
|
~domain=Complete,
|
||||||
~unit=TimeDistribution({zero: MomentRe.momentNow(), unit: `days}),
|
~unit=TimeDistribution({zero: MomentRe.momentNow(), unit: `days}),
|
||||||
|
|
|
@ -23,6 +23,37 @@ module ComplexPowerChart = {
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
let bar: DistributionTypes.xyShape = {
|
||||||
|
ys: [|0.5, 0.8, 0.4, 1.0, 2.0|],
|
||||||
|
xs: [|0.0, 1., 2., 5., 8.|],
|
||||||
|
};
|
||||||
|
|
||||||
|
module IntegralChart = {
|
||||||
|
[@react.component]
|
||||||
|
let make = (~complexPower: DistributionTypes.complexPower, ~onHover) => {
|
||||||
|
open DistFunctor.ComplexPower;
|
||||||
|
let integral =
|
||||||
|
DistFunctor.ComplexPower.T.Integral.get(~cache=None, complexPower);
|
||||||
|
let continuous =
|
||||||
|
integral
|
||||||
|
|> T.toContinuous
|
||||||
|
|> E.O.fmap(DistFunctor.Continuous.toLinear)
|
||||||
|
|> E.O.fmap(DistFunctor.Continuous.getShape);
|
||||||
|
let minX = T.minX(integral);
|
||||||
|
let maxX = T.maxX(integral);
|
||||||
|
let timeScale =
|
||||||
|
complexPower.unit |> DistributionTypes.DistributionUnit.toJson;
|
||||||
|
<CdfChart__Plain
|
||||||
|
minX
|
||||||
|
maxX
|
||||||
|
?continuous
|
||||||
|
color={`hex("333")}
|
||||||
|
timeScale
|
||||||
|
onHover
|
||||||
|
/>;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
[@react.component]
|
[@react.component]
|
||||||
let make = (~complexPower: DistributionTypes.complexPower) => {
|
let make = (~complexPower: DistributionTypes.complexPower) => {
|
||||||
let (x, setX) = React.useState(() => 0.);
|
let (x, setX) = React.useState(() => 0.);
|
||||||
|
@ -31,8 +62,14 @@ let make = (~complexPower: DistributionTypes.complexPower) => {
|
||||||
() => {<ComplexPowerChart complexPower onHover={r => {setX(_ => r)}} />},
|
() => {<ComplexPowerChart complexPower onHover={r => {setX(_ => r)}} />},
|
||||||
[|complexPower|],
|
[|complexPower|],
|
||||||
);
|
);
|
||||||
|
let chart2 =
|
||||||
|
React.useMemo1(
|
||||||
|
() => {<IntegralChart complexPower onHover={r => {setX(_ => r)}} />},
|
||||||
|
[|complexPower|],
|
||||||
|
);
|
||||||
<div>
|
<div>
|
||||||
chart
|
chart
|
||||||
|
chart2
|
||||||
<table className="table-auto">
|
<table className="table-auto">
|
||||||
<thead>
|
<thead>
|
||||||
<tr>
|
<tr>
|
||||||
|
|
|
@ -77,18 +77,28 @@ module Continuous = {
|
||||||
: option(DistributionTypes.continuousShape) =>
|
: option(DistributionTypes.continuousShape) =>
|
||||||
fn(xyShape) |> E.O.fmap(xyShape => make(xyShape, interpolation));
|
fn(xyShape) |> E.O.fmap(xyShape => make(xyShape, interpolation));
|
||||||
|
|
||||||
|
let toLinear = (t: t): t =>
|
||||||
|
switch (t) {
|
||||||
|
| {interpolation: `Stepwise, xyShape} => {
|
||||||
|
interpolation: `Linear,
|
||||||
|
xyShape: xyShape |> XYShape.Range.stepsToContinuous |> E.O.toExt(""),
|
||||||
|
}
|
||||||
|
| {interpolation: `Linear, _} => t
|
||||||
|
};
|
||||||
|
|
||||||
module T =
|
module T =
|
||||||
Dist({
|
Dist({
|
||||||
type t = DistributionTypes.continuousShape;
|
type t = DistributionTypes.continuousShape;
|
||||||
type integral = DistributionTypes.continuousShape;
|
type integral = DistributionTypes.continuousShape;
|
||||||
let shapeFn = (fn, t: t) => t |> xyShape |> fn;
|
let shapeFn = (fn, t: t) => t |> xyShape |> fn;
|
||||||
|
// TODO: Obviously fix this, it's terrible
|
||||||
let integral = (~cache, t) =>
|
let integral = (~cache, t) =>
|
||||||
cache
|
cache
|
||||||
|> E.O.default(
|
|> E.O.default(
|
||||||
t
|
t
|
||||||
|> xyShape
|
|> xyShape
|
||||||
|> XYShape.Range.integrateWithTriangles
|
|> XYShape.Range.integrateWithTriangles
|
||||||
|> E.O.toExt("")
|
|> E.O.toExt("Error1")
|
||||||
|> fromShape,
|
|> fromShape,
|
||||||
);
|
);
|
||||||
// This seems wrong, we really want the ending bit, I'd assume
|
// This seems wrong, we really want the ending bit, I'd assume
|
||||||
|
@ -118,7 +128,16 @@ module Discrete = {
|
||||||
type integral = DistributionTypes.continuousShape;
|
type integral = DistributionTypes.continuousShape;
|
||||||
let integral = (~cache, t) =>
|
let integral = (~cache, t) =>
|
||||||
cache
|
cache
|
||||||
|> E.O.default(t |> XYShape.accumulateYs |> Continuous.fromShape);
|
|> E.O.default(
|
||||||
|
{
|
||||||
|
Continuous.make(
|
||||||
|
XYShape.accumulateYs(t)
|
||||||
|
|> XYShape.Range.stepsToContinuous
|
||||||
|
|> E.O.toExt("ERROR"),
|
||||||
|
`Stepwise,
|
||||||
|
);
|
||||||
|
},
|
||||||
|
);
|
||||||
let integralSum = (~cache, t) => t |> XYShape.ySum;
|
let integralSum = (~cache, t) => t |> XYShape.ySum;
|
||||||
let minX = XYShape.minX;
|
let minX = XYShape.minX;
|
||||||
let maxX = XYShape.maxX;
|
let maxX = XYShape.maxX;
|
||||||
|
@ -197,26 +216,42 @@ module Mixed = {
|
||||||
DistributionTypes.MixedPoint.add(c, d);
|
DistributionTypes.MixedPoint.add(c, d);
|
||||||
};
|
};
|
||||||
|
|
||||||
let toScaledContinuous =
|
let scaleContinuous =
|
||||||
({continuous, discreteProbabilityMassFraction}: t) =>
|
({discreteProbabilityMassFraction}: t, continuous) =>
|
||||||
Some(
|
continuous
|
||||||
continuous
|
|> Continuous.T.scaleBy(~scale=1.0 -. discreteProbabilityMassFraction);
|
||||||
|> Continuous.T.scaleBy(
|
|
||||||
~scale=1.0 -. discreteProbabilityMassFraction,
|
|
||||||
),
|
|
||||||
);
|
|
||||||
|
|
||||||
let toScaledDiscrete = ({discrete, discreteProbabilityMassFraction}: t) =>
|
let scaleDiscrete = ({discreteProbabilityMassFraction}: t, disrete) =>
|
||||||
Some(
|
disrete |> Discrete.T.scaleBy(~scale=discreteProbabilityMassFraction);
|
||||||
discrete
|
|
||||||
|> Discrete.T.scaleBy(~scale=discreteProbabilityMassFraction),
|
let toScaledContinuous = ({continuous} as t: t) =>
|
||||||
);
|
Some(scaleContinuous(t, continuous));
|
||||||
|
|
||||||
|
let toScaledDiscrete = ({discrete} as t: t) =>
|
||||||
|
Some(scaleDiscrete(t, discrete));
|
||||||
|
|
||||||
// TODO: Add these two directly, once interpolation is added.
|
// TODO: Add these two directly, once interpolation is added.
|
||||||
let integral = (~cache, t) => {
|
let integral =
|
||||||
// let cont = scaledContinuousComponent(t);
|
(
|
||||||
// let discrete = scaledDiscreteComponent(t);
|
~cache,
|
||||||
cache |> E.O.toExt("");
|
{continuous, discrete, discreteProbabilityMassFraction} as t: t,
|
||||||
|
) => {
|
||||||
|
cache
|
||||||
|
|> E.O.default(
|
||||||
|
{
|
||||||
|
let cont =
|
||||||
|
continuous
|
||||||
|
|> Continuous.T.Integral.get(~cache=None)
|
||||||
|
|> scaleContinuous(t);
|
||||||
|
let dist =
|
||||||
|
discrete
|
||||||
|
|> Discrete.T.Integral.get(~cache=None)
|
||||||
|
|> Continuous.T.scaleBy(
|
||||||
|
~scale=discreteProbabilityMassFraction,
|
||||||
|
);
|
||||||
|
dist;
|
||||||
|
},
|
||||||
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
let integralSum =
|
let integralSum =
|
||||||
|
@ -323,7 +358,7 @@ module Shape = {
|
||||||
);
|
);
|
||||||
let minX = (t: t) =>
|
let minX = (t: t) =>
|
||||||
mapToAll(t, (Mixed.T.minX, Discrete.T.minX, Continuous.T.minX));
|
mapToAll(t, (Mixed.T.minX, Discrete.T.minX, Continuous.T.minX));
|
||||||
let integral = (~cache, t: t) =>
|
let integral = (~cache, t: t) => {
|
||||||
mapToAll(
|
mapToAll(
|
||||||
t,
|
t,
|
||||||
(
|
(
|
||||||
|
@ -332,6 +367,7 @@ module Shape = {
|
||||||
Continuous.T.Integral.get(~cache),
|
Continuous.T.Integral.get(~cache),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
|
};
|
||||||
let integralSum = (~cache, t: t) =>
|
let integralSum = (~cache, t: t) =>
|
||||||
mapToAll(
|
mapToAll(
|
||||||
t,
|
t,
|
||||||
|
|
|
@ -14,6 +14,11 @@ type xyShape = {
|
||||||
ys: array(float),
|
ys: array(float),
|
||||||
};
|
};
|
||||||
|
|
||||||
|
let foo = {xs: [|1., 2., 5.|], ys: [|1., 2., 3.|]};
|
||||||
|
let answer = {xs: [|1., 2., 2., 5., 5.|], ys: [|1., 1., 2., 2., 3.|]};
|
||||||
|
|
||||||
|
let toStepwise = (xyShape: xyShape) => {};
|
||||||
|
|
||||||
type interpolationMethod = [ | `Stepwise | `Linear];
|
type interpolationMethod = [ | `Stepwise | `Linear];
|
||||||
|
|
||||||
type continuousShape = {
|
type continuousShape = {
|
||||||
|
|
|
@ -15,8 +15,7 @@ let make =
|
||||||
unit,
|
unit,
|
||||||
};
|
};
|
||||||
|
|
||||||
let toComplexPower =
|
let toComplexPower = (~sampleCount, t: genericDistribution) => {
|
||||||
(~sampleCount, t: genericDistribution): option(complexPower) => {
|
|
||||||
let shape =
|
let shape =
|
||||||
switch (t.generationSource) {
|
switch (t.generationSource) {
|
||||||
| GuesstimatorString(s) =>
|
| GuesstimatorString(s) =>
|
||||||
|
|
|
@ -19,8 +19,24 @@ let zip = t => Belt.Array.zip(t.xs, t.ys);
|
||||||
|
|
||||||
let fmap = (t: t, y): t => {xs: t.xs, ys: t.ys |> E.A.fmap(y)};
|
let fmap = (t: t, y): t => {xs: t.xs, ys: t.ys |> E.A.fmap(y)};
|
||||||
|
|
||||||
|
let fromArray = ((xs, ys)): t => {xs, ys};
|
||||||
|
let fromArrays = (xs, ys): t => {xs, ys};
|
||||||
let pointwiseMap = (fn, t: t): t => {xs: t.xs, ys: t.ys |> E.A.fmap(fn)};
|
let pointwiseMap = (fn, t: t): t => {xs: t.xs, ys: t.ys |> E.A.fmap(fn)};
|
||||||
|
|
||||||
|
let intersperce = (t1: t, t2: t) => {
|
||||||
|
let foo: ref(array((float, float))) = ref([||]);
|
||||||
|
let t1 = zip(t1);
|
||||||
|
let t2 = zip(t2);
|
||||||
|
|
||||||
|
Belt.Array.forEachWithIndex(t1, (i, item) => {
|
||||||
|
switch (Belt.Array.get(t2, i)) {
|
||||||
|
| Some(r) => foo := E.A.append(foo^, [|item, r|])
|
||||||
|
| None => foo := E.A.append(foo^, [|item|])
|
||||||
|
}
|
||||||
|
});
|
||||||
|
foo^ |> Belt.Array.unzip |> fromArray;
|
||||||
|
};
|
||||||
|
|
||||||
let scaleCdfTo = (~scaleTo=1., t: t) =>
|
let scaleCdfTo = (~scaleTo=1., t: t) =>
|
||||||
switch (_lastElement(t.ys)) {
|
switch (_lastElement(t.ys)) {
|
||||||
| Some(n) =>
|
| Some(n) =>
|
||||||
|
@ -35,9 +51,6 @@ let yFold = (fn, t: t) => {
|
||||||
|
|
||||||
let ySum = yFold((a, b) => a +. b);
|
let ySum = yFold((a, b) => a +. b);
|
||||||
|
|
||||||
let fromArray = ((xs, ys)): t => {xs, ys};
|
|
||||||
let fromArrays = (xs, ys): t => {xs, ys};
|
|
||||||
|
|
||||||
let _transverse = fn =>
|
let _transverse = fn =>
|
||||||
Belt.Array.reduce(_, [||], (items, (x, y)) =>
|
Belt.Array.reduce(_, [||], (items, (x, y)) =>
|
||||||
switch (_lastElement(items)) {
|
switch (_lastElement(items)) {
|
||||||
|
@ -68,6 +81,12 @@ module Range = {
|
||||||
let rangeAreaAssumingSteps = (((lastX, lastY), (nextX, _)): zippedRange) =>
|
let rangeAreaAssumingSteps = (((lastX, lastY), (nextX, _)): zippedRange) =>
|
||||||
(nextX -. lastX) *. lastY;
|
(nextX -. lastX) *. lastY;
|
||||||
|
|
||||||
|
let rangePointAssumingSteps =
|
||||||
|
(((lastX, lastY), (nextX, nextY)): zippedRange) => (
|
||||||
|
nextX,
|
||||||
|
lastY,
|
||||||
|
);
|
||||||
|
|
||||||
let rangeAreaAssumingTriangles =
|
let rangeAreaAssumingTriangles =
|
||||||
(((lastX, lastY), (nextX, nextY)): zippedRange) =>
|
(((lastX, lastY), (nextX, nextY)): zippedRange) =>
|
||||||
(nextX -. lastX) *. (lastY +. nextY) /. 2.;
|
(nextX -. lastX) *. (lastY +. nextY) /. 2.;
|
||||||
|
@ -93,6 +112,15 @@ module Range = {
|
||||||
|> E.O.fmap(accumulateYs);
|
|> E.O.fmap(accumulateYs);
|
||||||
|
|
||||||
let derivative = mapYsBasedOnRanges(delta_y_over_delta_x);
|
let derivative = mapYsBasedOnRanges(delta_y_over_delta_x);
|
||||||
|
|
||||||
|
let stepsToContinuous = t =>
|
||||||
|
Belt.Array.zip(t.xs, t.ys)
|
||||||
|
|> E.A.toRanges
|
||||||
|
|> E.R.toOption
|
||||||
|
|> E.O.fmap(r => r |> Belt.Array.map(_, rangePointAssumingSteps))
|
||||||
|
|> E.O.fmap(Belt.Array.unzip)
|
||||||
|
|> E.O.fmap(fromArray)
|
||||||
|
|> E.O.fmap(intersperce(t));
|
||||||
};
|
};
|
||||||
|
|
||||||
let findY = CdfLibrary.Distribution.findY;
|
let findY = CdfLibrary.Distribution.findY;
|
||||||
|
|
Loading…
Reference in New Issue
Block a user