/// <summary>EP message to <c>sample</c>.</summary> /// <param name="choice">Incoming message from <c>choice</c>.</param> /// <param name="probTrue0">Constant value for <c>probTrue0</c>.</param> /// <param name="probTrue1">Constant value for <c>probTrue1</c>.</param> /// <returns>The outgoing EP message to the <c>sample</c> argument.</returns> /// <remarks> /// <para>The outgoing message is a distribution matching the moments of <c>sample</c> as the random arguments are varied. The formula is <c>proj[p(sample) sum_(choice) p(choice) factor(sample,choice,probTrue0,probTrue1)]/p(sample)</c>.</para> /// </remarks> public static Bernoulli SampleAverageConditional(Bernoulli choice, double probTrue0, double probTrue1) { Bernoulli result = new Bernoulli(); if (choice.IsPointMass) { return(SampleConditional(choice.Point, probTrue0, probTrue1)); } #if FAST result.SetProbTrue(choice.GetProbFalse() * probTrue0 + choice.GetProbTrue() * probTrue1); #else // This method is more numerically stable but slower. // let oX = log(p(X)/(1-p(X)) // let oY = log(p(Y)/(1-p(Y)) // oX = log( (TT*sigma(oY) + TF*sigma(-oY))/(FT*sigma(oY) + FF*sigma(-oY)) ) // = log( (TT*exp(oY) + TF)/(FT*exp(oY) + FF) ) // = log( (exp(oY) + TF/TT)/(exp(oY) + FF/FT) ) + log(TT/FT) // ay = log(TF/TT) // by = log(FF/FT) // offset = log(TT/FT) if (probTrue0 == 0 || probTrue1 == 0) { throw new ArgumentException("probTrue is zero"); } double ay = Math.Log(probTrue0 / probTrue1); double by = Math.Log((1 - probTrue0) / (1 - probTrue1)); double offset = MMath.Logit(probTrue1); result.LogOdds = MMath.DiffLogSumExp(choice.LogOdds, ay, by) + offset; #endif return(result); }
public Binomial(int trialCount, double probSuccess) { TrialCount = trialCount; LogOdds = MMath.Logit(probSuccess); A = 1; B = 1; }
/// <summary> /// Sets the probability of the binary variable being true /// </summary> public void SetProbTrue(double probTrue) { if (probTrue < 0 || probTrue > 1) { throw new ArgumentOutOfRangeException("probTrue", String.Format("probTrue = {0} is not in [0,1]", probTrue)); } LogOdds = MMath.Logit(probTrue); }
/// <summary> /// Creates a Bernoulli distribution with given probability of being true. /// </summary> /// <param name="probTrue">p(true)</param> public Bernoulli(double probTrue) { if (probTrue < 0 || probTrue > 1) { throw new ArgumentOutOfRangeException(nameof(probTrue), $"{nameof(probTrue)} = {probTrue} is not in [0,1]"); } LogOdds = MMath.Logit(probTrue); }
/// <summary> /// Sets the probability of the binary variable being false /// </summary> public void SetProbFalse(double probFalse) { if (probFalse < 0 || probFalse > 1) { throw new ArgumentOutOfRangeException(nameof(probFalse), $"{nameof(probFalse)} = {probFalse} is not in [0,1]"); } LogOdds = -MMath.Logit(probFalse); }
/// <summary> /// Creates a Bernoulli distribution with given probability of being true. /// </summary> /// <param name="probTrue">p(true)</param> public Bernoulli(double probTrue) { if (probTrue < 0 || probTrue > 1) { throw new ArgumentException(String.Format("probTrue = {0} is not in [0,1]", probTrue), "probTrue"); } LogOdds = MMath.Logit(probTrue); }
/// <summary> /// Sets the probability of the binary variable being false /// </summary> public void SetProbFalse(double probFalse) { if (probFalse < 0 || probFalse > 1) { throw new ArgumentException(String.Format("probFalse = {0} is not in [0,1]", probFalse), "probFalse"); } LogOdds = -MMath.Logit(probFalse); }
/// <summary> /// Sets the probability of the binary variable being true /// </summary> public void SetProbTrue(int index, double probTrue) { if (probTrue < 0 || probTrue > 1) { throw new ArgumentException(String.Format("probTrue = {0} is not in [0,1]", probTrue), "probTrue"); } LogOddsVector[index] = MMath.Logit(probTrue); }
/// <summary> /// Evidence message for EP /// </summary> /// <param name="logistic">Constant value for 'logistic'.</param> /// <param name="x">Incoming message from 'x'.</param> /// <returns>Logarithm of the factor's average value across the given argument distributions</returns> /// <remarks><para> /// The formula for the result is <c>log(sum_(x) p(x) factor(logistic,x))</c>. /// </para></remarks> public static double LogAverageFactor(double logistic, Gaussian x) { if (logistic >= 1.0 || logistic <= 0.0) { return(x.GetLogProb(MMath.Logit(logistic))); } // p(y,x) = delta(y - 1/(1+exp(-x))) N(x;mx,vx) // x = log(y/(1-y)) // dx = 1/(y*(1-y)) return(x.GetLogProb(MMath.Logit(logistic)) / (logistic * (1 - logistic))); }
/// <summary>VMP message to <c>sample</c>.</summary> /// <param name="choice">Incoming message from <c>choice</c>.</param> /// <param name="probTrue0">Constant value for <c>probTrue0</c>.</param> /// <param name="probTrue1">Constant value for <c>probTrue1</c>.</param> /// <returns>The outgoing VMP message to the <c>sample</c> argument.</returns> /// <remarks> /// <para>The outgoing message is the exponential of the average log-factor value, where the average is over all arguments except <c>sample</c>. The formula is <c>exp(sum_(choice) p(choice) log(factor(sample,choice,probTrue0,probTrue1)))</c>.</para> /// </remarks> public static Bernoulli SampleAverageLogarithm(Bernoulli choice, double probTrue0, double probTrue1) { Bernoulli result = new Bernoulli(); if (choice.IsPointMass) { return(SampleConditional(choice.Point, probTrue0, probTrue1)); } // log(p(X=true)/p(X=false)) = sum_k p(Y=k) log(ProbTrue[k]/(1-ProbTrue[k])) result.LogOdds = choice.GetProbFalse() * MMath.Logit(probTrue0) + choice.GetProbTrue() * MMath.Logit(probTrue1); return(result); }
/// <summary> /// Used to compute log odds in the above operator /// </summary> /// <param name="trueCount"></param> /// <param name="falseCount"></param> /// <returns></returns> internal static double ComputeLogOdds(double trueCount, double falseCount) { if (falseCount == Double.PositiveInfinity) { // compute log odds from prob true return(MMath.Logit(trueCount)); } else if ((trueCount == 0) || (falseCount == 0)) { throw new ImproperMessageException(new Beta(trueCount, falseCount)); } return(MMath.Digamma(trueCount) - MMath.Digamma(falseCount)); }
/// <summary> /// VMP message to 'sample'. /// </summary> /// <param name="index">Incoming message from 'index'.</param> /// <param name="ProbTrue">Constant value for 'probTrue'.</param> /// <returns>The outgoing VMP message to the 'sample' argument.</returns> /// <remarks><para> /// The outgoing message is the exponential of the integral of the log-factor times incoming messages, over all arguments except 'sample'. /// The formula is <c>int log(f(sample,x)) q(x) dx</c> where <c>x = (index,probTrue)</c>. /// </para></remarks> public static Bernoulli SampleAverageLogarithm(Discrete index, double[] ProbTrue) { Bernoulli result = new Bernoulli(); // E[sum_k I(Y=k) (X*log(ProbTrue[k]) + (1-X)*log(1-ProbTrue[k]))] // = X*(sum_k p(Y=k) log(ProbTrue[k])) + (1-X)*(sum_k p(Y=k) log(1-ProbTrue[k])) // p(X=true) =propto prod_k ProbTrue[k]^p(Y=k) // log(p(X=true)/p(X=false)) = sum_k p(Y=k) log(ProbTrue[k]/(1-ProbTrue[k])) double s = 0; for (int i = 0; i < index.Dimension; i++) { s += index[i] * MMath.Logit(ProbTrue[i]); } result.LogOdds = s; return(result); }
[NoTriggers] // see VmpTests.AdditiveSparseBlockmodel public static double A([Proper, SkipIfUniform] Gaussian x, double a) { double m, v; x.GetMeanAndVariance(out m, out v); double newa = .5 - (MMath.Logit(a) - m) / v; double normala = MMath.Logistic(m + (1.0 - 2.0 * a) * v / 2.0); if (logSumExpBound(m, v, normala) > logSumExpBound(m, v, newa)) { return(newa); } else { return(normala); } }
/// <summary>EP message to <c>choice</c>.</summary> /// <param name="sample">Incoming message from <c>sample</c>. Must be a proper distribution. If uniform, the result will be uniform.</param> /// <param name="probTrue0">Constant value for <c>probTrue0</c>.</param> /// <param name="probTrue1">Constant value for <c>probTrue1</c>.</param> /// <returns>The outgoing EP message to the <c>choice</c> argument.</returns> /// <remarks> /// <para>The outgoing message is a distribution matching the moments of <c>choice</c> as the random arguments are varied. The formula is <c>proj[p(choice) sum_(sample) p(sample) factor(sample,choice,probTrue0,probTrue1)]/p(choice)</c>.</para> /// </remarks> /// <exception cref="ImproperMessageException"> /// <paramref name="sample" /> is not a proper distribution.</exception> public static Bernoulli ChoiceAverageConditional([SkipIfUniform] Bernoulli sample, double probTrue0, double probTrue1) { Bernoulli result = new Bernoulli(); if (sample.IsPointMass) { return(ChoiceConditional(sample.Point, probTrue0, probTrue1)); } #if FAST double p1 = sample.GetProbFalse() * (1 - probTrue1) + sample.GetProbTrue() * probTrue1; double p0 = sample.GetProbFalse() * (1 - probTrue0) + sample.GetProbTrue() * probTrue0; double sum = p0 + p1; if (sum == 0.0) { throw new AllZeroException(); } else { result.SetProbTrue(p1 / sum); } #else // This method is more numerically stable but slower. // ax = log(FT/TT) // bx = log(FF/TF) // offset = log(TT/TF) if (probTrue0 == 0 || probTrue1 == 0) { throw new ArgumentException("probTrue is zero"); } double ax = -MMath.Logit(probTrue1); double bx = -MMath.Logit(probTrue0); double offset = Math.Log(probTrue1 / probTrue0); result.LogOdds = MMath.DiffLogSumExp(sample.LogOdds, ax, bx) + offset; #endif return(result); }
/// <summary> /// Creates a list of Bernoullis of the specified size, each set to have the specified probability of being true. /// </summary> /// <param name="size">The size of the list</param> /// <param name="probTrue">The probability of each Bernoulli being true</param> public SparseBernoulliList(int size, double probTrue) { LogOddsVector = ApproximateSparseVector.Constant(size, MMath.Logit(probTrue), DefaultSparsity); }
/// <summary> /// EP message to 'x' /// </summary> /// <param name="logistic">Constant value for 'logistic'.</param> /// <returns>The outgoing EP message to the 'x' argument</returns> /// <remarks><para> /// The outgoing message is the factor viewed as a function of 'x' conditioned on the given values. /// </para></remarks> public static Gaussian XAverageConditional(double logistic) { return(Gaussian.PointMass(MMath.Logit(logistic))); }
/// <include file='FactorDocs.xml' path='factor_docs/message_op_class[@name="DiscreteAreEqualOp"]/message_doc[@name="AreEqualAverageConditional(int, Discrete)"]/*'/> public static Bernoulli AreEqualAverageConditional(int A, Discrete B) { return(Bernoulli.FromLogOdds(MMath.Logit(B[A]))); }
/// <include file='FactorDocs.xml' path='factor_docs/message_op_class[@name="DiscreteAreEqualOp"]/message_doc[@name="AreEqualAverageConditional(Discrete, Discrete)"]/*'/> public static Bernoulli AreEqualAverageConditional(Discrete A, Discrete B) { return(Bernoulli.FromLogOdds(MMath.Logit(A.ProbEqual(B)))); }
/// <summary> /// Sets this BernoulliIntegerSubset distribution to the weighted sum of two other such distributions /// </summary> /// <param name="weight1"></param> /// <param name="value1"></param> /// <param name="weight2"></param> /// <param name="value2"></param> /// <remarks>Not yet implemented</remarks> public void SetToSum(double weight1, BernoulliIntegerSubset value1, double weight2, BernoulliIntegerSubset value2) { if (weight1 + weight2 == 0) { SetToUniform(); } else { LogOddsVector.SetToFunction(value1.GetProbTrueVector(), value2.GetProbTrueVector(), (x, y) => MMath.Logit((weight1 * x + weight2 * y) / (weight1 + weight2))); } }