コード例 #1
0
        private void init(int n1, int n2, double[] ranks, bool?exact)
        {
            int n = n1 + n2;

            this.n1 = n1;
            this.n2 = n2;

            // From https://en.wikipedia.org/wiki/Mann%E2%80%93Whitney_U_test: For large samples, U
            // is approximately normally distributed. In that case, the standardized value is given
            // by z = (U - mean) / stdDev where:
            double mean   = (n1 * n2) / 2.0;
            double stdDev = Math.Sqrt((n1 * n2 * (n + 1)) / 12.0);

            bool hasVectors = ranks != null;

            // For small samples (< 30) the distribution can be exact
            this.exact = hasVectors && (n1 <= 30 && n2 <= 30);

            if (exact.HasValue)
            {
                if (exact.Value && !hasVectors)
                {
                    throw new ArgumentException("exact", "Cannot use exact method if rank vectors are not specified.");
                }
                this.exact = exact.Value; // force
            }

            if (hasVectors)
            {
                // Apply correction to the variance
                double correction = MannWhitneyDistribution.correction(ranks);
                stdDev = Math.Sqrt((n1 * n2 * ((n + 1.0) - correction)) / 12.0);

                if (this.exact)
                {
                    initExactMethod(ranks);
                }
            }

            this.approximation = new NormalDistribution(mean, stdDev);
        }
コード例 #2
0
        private void init(int n1, int n2, double[] ranks, bool?exact)
        {
            if (n1 <= 0)
            {
                throw new ArgumentOutOfRangeException("n1", "The number of observations in the first sample (n1) must be higher than zero.");
            }

            if (n2 <= 0)
            {
                throw new ArgumentOutOfRangeException("n2", "The number of observations in the second sample (n2) must be higher than zero.");
            }

            if (n1 > n2)
            {
                Trace.TraceWarning("Creating a MannWhitneyDistribution where the first sample is larger than the second sample. If possible, please re-organize your samples such that the first sample is smaller than the second sample.");
            }

            if (ranks != null)
            {
                if (ranks.Length <= 1)
                {
                    throw new ArgumentOutOfRangeException("ranks", "The rank vector must contain a minimum of 2 elements.");
                }

                for (int i = 0; i < ranks.Length; i++)
                {
                    if (ranks[i] < 0)
                    {
                        throw new ArgumentOutOfRangeException("The rank values cannot be negative.");
                    }
                }
            }

            int n = n1 + n2;

            this.n1 = n1;
            this.n2 = n2;

            // From https://en.wikipedia.org/wiki/Mann%E2%80%93Whitney_U_test: For large samples, U
            // is approximately normally distributed. In that case, the standardized value is given
            // by z = (U - mean) / stdDev where:
            double mean   = ((double)n1 * n2) / 2.0;
            double stdDev = Math.Sqrt(((double)n1 * n2 * (n + 1)) / 12.0);

            bool hasVectors = ranks != null;

            // For small samples (< 30) the distribution can be exact
            this.exact = hasVectors && (n1 <= 30 && n2 <= 30);

            if (exact.HasValue)
            {
                if (exact.Value && !hasVectors)
                {
                    throw new ArgumentException("exact", "Cannot use exact method if rank vectors are not specified.");
                }
                this.exact = exact.Value; // force
            }

            if (hasVectors)
            {
                // Apply correction to the variance
                double correction = MannWhitneyDistribution.correction(ranks);
                double a          = ((double)n1 * n2) / 12.0;
                double b          = (n + 1.0) - correction;
                stdDev = Math.Sqrt(a * b);

                if (this.exact)
                {
                    initExactMethod(ranks);
                }
            }

            this.approximation = new NormalDistribution(mean, stdDev);
        }