private static BiasResults GetProbePoolBiasScore(VariantComparisonCase Case, CalledAllele Consensus,
                                                         float ProbePoolBiasThreshold, VariantCallingParameters variantCallingParameters, int AltCountA, int AltCountB, int DepthA, int DepthB, Genotype Genotype, bool AltChangeToRef)
        {
            double      ProbePoolPScore        = 0;    //no bias;
            double      ProbePoolGATKBiasScore = -100; //no bias;
            int         NoiseLevel             = Consensus.NoiseLevelApplied;
            BiasResults PB = new BiasResults();

            if ((AltChangeToRef) || (Case == VariantComparisonCase.AgreedOnReference))
            {
                PB.GATKBiasScore = ProbePoolGATKBiasScore;
                PB.BiasScore     = ProbePoolPScore;
                return(PB);
            }

            if ((Case == VariantComparisonCase.OneReferenceOneAlternate) ||
                (Case == VariantComparisonCase.CanNotCombine))
            {
                Consensus.Filters.Add(FilterType.PoolBias);
                PB.GATKBiasScore = 0;
                PB.BiasScore     = 1;
                return(PB);
            }

            if (Case == VariantComparisonCase.AgreedOnAlternate)
            {
                int[] supportByPool = new int[]
                {
                    AltCountA, AltCountB, 0
                };
                int[] covByPool = new int[]
                {
                    DepthA, DepthB, 0
                };


                BiasResults ProbePoolBiasResults =
                    StrandBiasCalculator.CalculateStrandBiasResults(
                        covByPool, supportByPool,
                        NoiseLevel, variantCallingParameters.MinimumFrequency, ProbePoolBiasThreshold, StrandBiasModel.Extended);

                ProbePoolGATKBiasScore = Math.Min(0, ProbePoolBiasResults.GATKBiasScore);        //just cap it at upperbound 0, dont go higher.
                ProbePoolGATKBiasScore = Math.Max(-100, ProbePoolGATKBiasScore);                 //just cap it at lowerbound -100, dont go higher.

                ProbePoolPScore = Math.Min(1, ProbePoolBiasResults.BiasScore);

                if (!ProbePoolBiasResults.BiasAcceptable)
                {
                    Consensus.Filters.Add(FilterType.PoolBias);
                }
            }

            PB.GATKBiasScore = ProbePoolGATKBiasScore;
            PB.BiasScore     = ProbePoolPScore;
            return(PB);
        }
        public void TestSBCalculationsForForcedVariants()
        {
            var CoverageByStrandDirection = new int[] { 70038, 65998, 0 }; //forward,reverse,stitched
            var SupportByStrandDirection  = new int[] { 54, 11, 0 };

            BiasResults SB = StrandBiasCalculator.CalculateStrandBiasResults(
                CoverageByStrandDirection, SupportByStrandDirection, 20, 0.01, 0.5, StrandBiasModel.Poisson);

            Assert.Equal(SB.BiasScore, 1.0);

            Assert.Equal(SB.GATKBiasScore, 0);
        }
        public void TestSBCalculationsForSomaticAndDiploidSettings()
        {
            double fwdCov           = 10000;
            double revCov           = 10000;
            double testVariantFreqA = 0.05;
            double testVariantFreqB = 0.25;
            double testVariantFreqC = 0.020;
            double testVariantFreqD = 0.005;

            var CoverageByStrandDirection      = new int[] { (int)fwdCov, (int)revCov, 0 }; //forward,reverse,stitched
            var EqualSupportByStrandDirectionA = new int[] { (int)(fwdCov * testVariantFreqA), (int)(revCov * testVariantFreqA), 0 };
            var EqualSupportByStrandDirectionB = new int[] { (int)(fwdCov * testVariantFreqB), (int)(revCov * testVariantFreqB), 0 };

            //happy path, no bias

            BiasResults SB_somatic = StrandBiasCalculator.CalculateStrandBiasResults(
                CoverageByStrandDirection, EqualSupportByStrandDirectionB, 20, 0.01, 0.5, StrandBiasModel.Extended);

            BiasResults SB_diploid = StrandBiasCalculator.CalculateStrandBiasResults(
                CoverageByStrandDirection, EqualSupportByStrandDirectionB, 20, 0.20, 0.5, StrandBiasModel.Diploid);

            Assert.Equal(SB_somatic.BiasScore, 0);
            Assert.Equal(SB_somatic.GATKBiasScore, double.NegativeInfinity);
            Assert.Equal(SB_somatic.BiasAcceptable, true);

            Assert.Equal(SB_diploid.BiasScore, 0);
            Assert.Equal(SB_diploid.GATKBiasScore, double.NegativeInfinity);
            Assert.Equal(SB_diploid.BiasAcceptable, true);

            //bias if you are looking for a 20% variant (only one side is sufficient to call),
            //but not biased in the somatic case (both show up sufficiently)

            var SupportByStrandDirection_bias20 = new int[] { (int)(fwdCov * testVariantFreqA), (int)(revCov * testVariantFreqB), 0 };

            SB_somatic = StrandBiasCalculator.CalculateStrandBiasResults(
                CoverageByStrandDirection, SupportByStrandDirection_bias20, 20, 0.01, 0.5, StrandBiasModel.Extended);
            SB_diploid = StrandBiasCalculator.CalculateStrandBiasResults(
                CoverageByStrandDirection, SupportByStrandDirection_bias20, 20, 0.20, 0.5, StrandBiasModel.Diploid);

            Assert.Equal(SB_somatic.BiasScore, 0);
            Assert.Equal(SB_somatic.GATKBiasScore, double.NegativeInfinity);
            Assert.Equal(SB_somatic.BiasAcceptable, true);

            Assert.Equal(Math.Log10(SB_diploid.BiasScore), 74.3, 1);  // a great big bias
            Assert.Equal(SB_diploid.GATKBiasScore, 743.5, 1);
            Assert.Equal(SB_diploid.BiasAcceptable, false);

            //bias if you are looking for even a 1% variant or a 20% variant

            var SupportByStrandDirection_bias01 = new int[] { (int)(fwdCov * testVariantFreqC), (int)(revCov * testVariantFreqD), 0 };

            SB_somatic = StrandBiasCalculator.CalculateStrandBiasResults(
                CoverageByStrandDirection, SupportByStrandDirection_bias01, 20, 0.01, 0.5, StrandBiasModel.Extended);
            SB_diploid = StrandBiasCalculator.CalculateStrandBiasResults(
                CoverageByStrandDirection, SupportByStrandDirection_bias01, 20, 0.20, 0.5, StrandBiasModel.Diploid);

            Assert.Equal(SB_somatic.BiasScore, 1.000, 3);
            Assert.Equal(SB_somatic.GATKBiasScore, 0.002, 3);
            Assert.Equal(SB_somatic.BiasAcceptable, false);

            Assert.Equal(SB_diploid.BiasScore, 1.000, 3);// a great big bias
            Assert.Equal(SB_diploid.GATKBiasScore, 0.000, 3);
            Assert.Equal(SB_diploid.BiasAcceptable, false);
        }