@@ -1271,44 +1271,44 @@ def genotype_likelihood(
12711271 return {"0/0" : 1.0 , "0/1" : 0.0 , "1/1" : 0.0 }
12721272
12731273 # Generate all possible genotypes for this copy number
1274- # For CN=n, we can have 0 to n copies of the alt allele
1274+ # For CN=n, we can have 0 to n copies of the alt allele.
1275+ # Use a small error rate epsilon to model read noise/ref-overcounting.
1276+ epsilon = 0.05
12751277 genotype_probs = {}
12761278
12771279 if cn == 1 :
12781280 # Haploid (e.g., male X/Y chromosomes, or deletions reducing CN to 1)
12791281 # Possible genotypes: 0 (ref) or 1 (alt)
12801282 genotype_probs = {
1281- "0" : 0.01 , # ~0% alt reads expected
1282- "1" : 0.50 , # ~50 % alt reads expected (bias towards variant calling)
1283+ "0" : epsilon , # ~0% alt reads expected, allowing noise
1284+ "1" : 1.0 - epsilon , # ~100 % alt reads expected, allowing occasional ref reads
12831285 }
12841286 elif cn == 2 :
12851287 # Diploid (normal autosomal)
12861288 # Possible genotypes: 0/0, 0/1, 1/1
12871289 genotype_probs = {
1288- "0/0" : 0.01 , # ~0% alt reads expected
1289- "0/1" : 0.45 , # ~45% alt reads expected
1290- "1/1" : (
1291- 0.90 # ~90% alt reads expected (compensate n_total_reads overestimation)
1292- ),
1290+ "0/0" : epsilon , # ~0% alt reads expected
1291+ "0/1" : 0.5 , # exact half alt reads expected
1292+ "1/1" : 1.0 - epsilon , # ~100% alt reads expected
12931293 }
12941294 elif cn == 3 :
12951295 # Triploid (duplication)
12961296 # Possible genotypes: 0/0/0, 0/0/1, 0/1/1, 1/1/1
12971297 genotype_probs = {
1298- "0/0/0" : 0.01 , # ~0% alt reads
1299- "0/0/1" : 1.0 / 3.0 , # ~33% alt reads
1300- "0/1/1" : 2.0 / 3.0 , # ~67% alt reads
1301- "1/1/1" : 0.99 , # ~100% alt reads
1298+ "0/0/0" : epsilon ,
1299+ "0/0/1" : 1.0 / 3.0 ,
1300+ "0/1/1" : 2.0 / 3.0 ,
1301+ "1/1/1" : 1.0 - epsilon ,
13021302 }
13031303 elif cn == 4 :
13041304 # Tetraploid
13051305 # Possible genotypes: 0/0/0/0, 0/0/0/1, 0/0/1/1, 0/1/1/1, 1/1/1/1
13061306 genotype_probs = {
1307- "0/0/0/0" : 0.01 , # ~0% alt reads
1308- "0/0/0/1" : 0.25 , # ~25% alt reads
1309- "0/0/1/1" : 0.50 , # ~50% alt reads
1310- "0/1/1/1" : 0.75 , # ~75% alt reads
1311- "1/1/1/1" : 0.99 , # ~100% alt reads
1307+ "0/0/0/0" : epsilon ,
1308+ "0/0/0/1" : 0.25 ,
1309+ "0/0/1/1" : 0.50 ,
1310+ "0/1/1/1" : 0.75 ,
1311+ "1/1/1/1" : 1.0 - epsilon ,
13121312 }
13131313 else :
13141314 # General case for CN > 4 or CN == 0
@@ -1320,11 +1320,7 @@ def genotype_likelihood(
13201320 for n_alt_copies in range (cn + 1 ):
13211321 genotype = "/" .join (["1" if i < n_alt_copies else "0" for i in range (cn )])
13221322 expected_alt_fraction = n_alt_copies / cn if cn > 0 else 0.0
1323- # Use small epsilon for 0 and 1 to avoid edge effects
1324- if expected_alt_fraction == 0.0 :
1325- expected_alt_fraction = 0.01
1326- elif expected_alt_fraction == 1.0 :
1327- expected_alt_fraction = 0.99
1323+ expected_alt_fraction = min (max (expected_alt_fraction , epsilon ), 1.0 - epsilon )
13281324 genotype_probs [genotype ] = expected_alt_fraction
13291325
13301326 # Compute binomial probabilities for each genotype
0 commit comments