您当前的位置: 首页 > 

寒冰屋

暂无认证

  • 0浏览

    0关注

    2286博文

    0收益

  • 0浏览

    0点赞

    0打赏

    0留言

私信
关注
热门博文

大型Lambda的C# 泊松累积分布

寒冰屋 发布时间:2020-04-11 16:56:51 ,浏览量:0

目录

介绍

背景

使用代码

  • 下载源8.7 KB
介绍

用Ramanujan的阶乘近似值计算C#中的泊松分布

背景

如果需要用于很大型Lambda的泊松累积分布函数,则可以使用此代码。

使用代码

泊松概率质量函数的公式为:

F(k,\lambda )=\sum_{i=0}^{k}\frac{e^{-\lambda} \lambda^i}{i!} 

在C#中,可以将其计算为:

public double Cdf(long k)
{
    var e = Math.Pow(Math.E, -_lambda);
    long i = 0;
    var sum = 0.0;
    while (i 
  • \ln(e^y) = y
  • e^{\ln(x)} = x = e^{\ln(x)} = y = x=y,forx =0
  • \ln(x/y) = \ln(x) - \ln(y)
  • \ln(x*y) = \ln(x) + \ln(y)
  • 计算使用对数和Ramanujan的阶乘近似表示:

    \ln(n!) \approx n\ln(n)-n+\frac{\ln(n(1+4n(1+2n)))}{6} +\frac{\ln(\Pi )}{2} 

    请在此处详细了解。

    设置Math.Pow(_lambda, i) / Factorial(i)= (A) = (\frac{\lambda ^{i}}{i!})给出了

     \ln(A) = \ln(\frac{\lambda^i}{i!}) =\ln(A) =\ln(\lambda^i) -\ln(i!)

    通过使用Ramanujan的阶乘近似,我们得到:

    使用C#表示法并利用e^{\ln(x)} =x,我们得到:

    A = Math.Pow(e, i*ln(ℷ) -i*ln(i) + i - ln(i*(1 + 4*i*(1 + 2*i)))/6 - ln(π)/2))

    可以在C#计算中使用此表达式,如以下代码所示:

    var log6ThTail = Math.Log(i * (1 + 4 * i * (1 + 2 * i)))/6;
    var lnN = i * Math.Log(_lambda) - (i * Math.Log(i) - i + log6ThTail + logPiDivTwo);
    n = Math.Pow(Math.E, lnN - _lambda);

    这是代码:

    using System;
    
    namespace PoissonEvaluator
    {
    	public class PoissonDistribution
    	{
    		private readonly double _lambda;
    
    		public PoissonDistribution(double lambda = 1.0)
    		{
    			_lambda = lambda;
    		}
    
    		public double Pmf(long k)
    		{
    			if (k > 170 || double.IsInfinity(Math.Pow(_lambda, k)))
    			{
    				var logLambda = k * Math.Log(_lambda) - 
                                            _lambda - (k * Math.Log(k) - k +
    					Math.Log(k * (1 + 4 * k * (1 + 2 * k))) / 6 + 
                                            Math.Log(Math.PI) / 2);
    				return Math.Pow(Math.E, logLambda);
    			}
    			return Math.Pow(Math.E, -_lambda) * Math.Pow(_lambda, k) / Factorial(k);
    		}
    
    		public double Cdf(long k)
    		{
    			long i = 0;
    			var sum = 0.0;
    			var infinityIsFound = false;
    			var eLambda = Math.Pow(Math.E, -_lambda);
    			var logPiDivTwo = Math.Log(Math.PI) / 2;
    			while (i  170 || double.IsInfinity(Math.Pow(_lambda, i)))
    					{
    						infinityIsFound = true;
    						var log6ThTail = Math.Log
                                                        (i * (1 + 4 * i * (1 + 2 * i))) / 6;
    						var lnN = i * Math.Log(_lambda) - 
                                                                (i * Math.Log(i) - i +
    							log6ThTail + logPiDivTwo);
    						n = Math.Pow(Math.E, lnN - _lambda);
    					}
    					else
    					{
    						n = eLambda * Math.Pow(_lambda, i) / Factorial(i);
    					}
    				}
    
    				sum += n;
    				i++;
    			}
    			return (sum > 1) ? 1.0 : sum;
    		}
    
    
    		public double Factorial(long k)
    		{
    			long count = k;
    			double factorial = 1;
    			while (count >= 1)
    			{
    				factorial = factorial * count;
    				count--;
    			}
    
    			return factorial;
    		}
    	}

     

    关注
    打赏
    1665926880
    查看更多评论
    0.1369s