11use  crate :: Error ; 
22// use std::f64::consts::PI; 
33
4- 
54// Import C library functions properly 
65unsafe  extern  "C"  { 
76    fn  exp ( x :  f64 )  -> f64 ; 
@@ -197,7 +196,7 @@ pub fn tgamma(x: f64) -> Result<f64, Error> {
197196        let  lanczos = lanczos_sum ( absx) ; 
198197        let  mut  r = term3 / lanczos; 
199198        r -= z *  r; 
200-          
199+ 
201200        if  absx < 140.0  { 
202201            unsafe  {  r / pow ( y,  absx - 0.5 )  } 
203202        }  else  { 
@@ -211,7 +210,7 @@ pub fn tgamma(x: f64) -> Result<f64, Error> {
211210        let  exp_y = unsafe  {  exp ( y)  } ; 
212211        let  mut  r = lanczos / exp_y; 
213212        r += z *  r; 
214-          
213+ 
215214        if  absx < 140.0  { 
216215            unsafe  {  r *  pow ( y,  absx - 0.5 )  } 
217216        }  else  { 
@@ -261,19 +260,19 @@ pub fn lgamma(x: f64) -> Result<f64, Error> {
261260    // Using C's math functions through libc to match CPython 
262261    let  lanczos_sum_val = lanczos_sum ( absx) ; 
263262    let  log_lanczos = unsafe  {  log ( lanczos_sum_val)  } ; 
264-      
263+ 
265264    // Subtract lanczos_g as a separate step 
266265    let  mut  r = log_lanczos - LANCZOS_G ; 
267-      
266+ 
268267    // Calculate (absx - 0.5) term 
269268    let  factor = absx - 0.5 ; 
270-      
269+ 
271270    // Calculate log term 
272271    let  log_term = unsafe  {  log ( absx + LANCZOS_G  - 0.5 )  } ; 
273-      
272+ 
274273    // Calculate the multiplication and subtraction 
275274    let  step2 = factor *  ( log_term - 1.0 ) ; 
276-      
275+ 
277276    // Combine the results 
278277    r += step2; 
279278
@@ -283,11 +282,11 @@ pub fn lgamma(x: f64) -> Result<f64, Error> {
283282        let  abs_sinpi = unsafe  {  fabs ( sinpi_val)  } ; 
284283        let  log_abs_sinpi = unsafe  {  log ( abs_sinpi)  } ; 
285284        let  log_absx = unsafe  {  log ( absx)  } ; 
286-          
285+ 
287286        // Combine in exactly the same order as CPython 
288287        r = LOG_PI  - log_abs_sinpi - log_absx - r; 
289288    } 
290-      
289+ 
291290    if  r. is_infinite ( )  { 
292291        return  Err ( Error :: ERANGE ) ; 
293292    } 
@@ -328,9 +327,73 @@ mod tests {
328327        } 
329328    } 
330329
330+     #[ test]  
331+     fn  test_literal ( )  { 
332+         // Verify single constants 
333+         assert_eq ! ( PI ,  3.141592653589793238462643383279502884197 ) ; 
334+         assert_eq ! ( LOG_PI ,  1.144729885849400174143427351353058711647 ) ; 
335+         assert_eq ! ( LANCZOS_G ,  6.024680040776729583740234375 ) ; 
336+         assert_eq ! ( LANCZOS_G_MINUS_HALF ,  5.524680040776729583740234375 ) ; 
337+ 
338+         // Verify LANCZOS_NUM_COEFFS 
339+         assert_eq ! ( LANCZOS_NUM_COEFFS [ 0 ] ,  23531376880.410759 ) ; 
340+         assert_eq ! ( LANCZOS_NUM_COEFFS [ 1 ] ,  42919803642.649101 ) ; 
341+         assert_eq ! ( LANCZOS_NUM_COEFFS [ 2 ] ,  35711959237.355667 ) ; 
342+         assert_eq ! ( LANCZOS_NUM_COEFFS [ 3 ] ,  17921034426.037209 ) ; 
343+         assert_eq ! ( LANCZOS_NUM_COEFFS [ 4 ] ,  6039542586.3520279 ) ; 
344+         assert_eq ! ( LANCZOS_NUM_COEFFS [ 5 ] ,  1439720407.3117216 ) ; 
345+         assert_eq ! ( LANCZOS_NUM_COEFFS [ 6 ] ,  248874557.86205417 ) ; 
346+         assert_eq ! ( LANCZOS_NUM_COEFFS [ 7 ] ,  31426415.585400194 ) ; 
347+         assert_eq ! ( LANCZOS_NUM_COEFFS [ 8 ] ,  2876370.6289353725 ) ; 
348+         assert_eq ! ( LANCZOS_NUM_COEFFS [ 9 ] ,  186056.26539522348 ) ; 
349+         assert_eq ! ( LANCZOS_NUM_COEFFS [ 10 ] ,  8071.6720023658163 ) ; 
350+         assert_eq ! ( LANCZOS_NUM_COEFFS [ 11 ] ,  210.82427775157936 ) ; 
351+         assert_eq ! ( LANCZOS_NUM_COEFFS [ 12 ] ,  2.5066282746310002 ) ; 
352+ 
353+         // Verify LANCZOS_DEN_COEFFS 
354+         assert_eq ! ( LANCZOS_DEN_COEFFS [ 0 ] ,  0.0 ) ; 
355+         assert_eq ! ( LANCZOS_DEN_COEFFS [ 1 ] ,  39916800.0 ) ; 
356+         assert_eq ! ( LANCZOS_DEN_COEFFS [ 2 ] ,  120543840.0 ) ; 
357+         assert_eq ! ( LANCZOS_DEN_COEFFS [ 3 ] ,  150917976.0 ) ; 
358+         assert_eq ! ( LANCZOS_DEN_COEFFS [ 4 ] ,  105258076.0 ) ; 
359+         assert_eq ! ( LANCZOS_DEN_COEFFS [ 5 ] ,  45995730.0 ) ; 
360+         assert_eq ! ( LANCZOS_DEN_COEFFS [ 6 ] ,  13339535.0 ) ; 
361+         assert_eq ! ( LANCZOS_DEN_COEFFS [ 7 ] ,  2637558.0 ) ; 
362+         assert_eq ! ( LANCZOS_DEN_COEFFS [ 8 ] ,  357423.0 ) ; 
363+         assert_eq ! ( LANCZOS_DEN_COEFFS [ 9 ] ,  32670.0 ) ; 
364+         assert_eq ! ( LANCZOS_DEN_COEFFS [ 10 ] ,  1925.0 ) ; 
365+         assert_eq ! ( LANCZOS_DEN_COEFFS [ 11 ] ,  66.0 ) ; 
366+         assert_eq ! ( LANCZOS_DEN_COEFFS [ 12 ] ,  1.0 ) ; 
367+ 
368+         // Verify GAMMA_INTEGRAL 
369+         assert_eq ! ( GAMMA_INTEGRAL [ 0 ] ,  1.0 ) ; 
370+         assert_eq ! ( GAMMA_INTEGRAL [ 1 ] ,  1.0 ) ; 
371+         assert_eq ! ( GAMMA_INTEGRAL [ 2 ] ,  2.0 ) ; 
372+         assert_eq ! ( GAMMA_INTEGRAL [ 3 ] ,  6.0 ) ; 
373+         assert_eq ! ( GAMMA_INTEGRAL [ 4 ] ,  24.0 ) ; 
374+         assert_eq ! ( GAMMA_INTEGRAL [ 5 ] ,  120.0 ) ; 
375+         assert_eq ! ( GAMMA_INTEGRAL [ 6 ] ,  720.0 ) ; 
376+         assert_eq ! ( GAMMA_INTEGRAL [ 7 ] ,  5040.0 ) ; 
377+         assert_eq ! ( GAMMA_INTEGRAL [ 8 ] ,  40320.0 ) ; 
378+         assert_eq ! ( GAMMA_INTEGRAL [ 9 ] ,  362880.0 ) ; 
379+         assert_eq ! ( GAMMA_INTEGRAL [ 10 ] ,  3628800.0 ) ; 
380+         assert_eq ! ( GAMMA_INTEGRAL [ 11 ] ,  39916800.0 ) ; 
381+         assert_eq ! ( GAMMA_INTEGRAL [ 12 ] ,  479001600.0 ) ; 
382+         assert_eq ! ( GAMMA_INTEGRAL [ 13 ] ,  6227020800.0 ) ; 
383+         assert_eq ! ( GAMMA_INTEGRAL [ 14 ] ,  87178291200.0 ) ; 
384+         assert_eq ! ( GAMMA_INTEGRAL [ 15 ] ,  1307674368000.0 ) ; 
385+         assert_eq ! ( GAMMA_INTEGRAL [ 16 ] ,  20922789888000.0 ) ; 
386+         assert_eq ! ( GAMMA_INTEGRAL [ 17 ] ,  355687428096000.0 ) ; 
387+         assert_eq ! ( GAMMA_INTEGRAL [ 18 ] ,  6402373705728000.0 ) ; 
388+         assert_eq ! ( GAMMA_INTEGRAL [ 19 ] ,  1.21645100408832e+17 ) ; 
389+         assert_eq ! ( GAMMA_INTEGRAL [ 20 ] ,  2.43290200817664e+18 ) ; 
390+         assert_eq ! ( GAMMA_INTEGRAL [ 21 ] ,  5.109094217170944e+19 ) ; 
391+         assert_eq ! ( GAMMA_INTEGRAL [ 22 ] ,  1.1240007277776077e+21 ) ; 
392+     } 
393+ 
331394    #[ test]  
332395    fn  test_specific_lgamma_value ( )  { 
333-         let  x = - 3.8510064710745118 ; 
396+         let  x = 0.003585187864492183 ; 
334397        let  rs_lgamma = lgamma ( x) . unwrap ( ) ; 
335398
336399        pyo3:: prepare_freethreaded_python ( ) ; 
@@ -385,6 +448,42 @@ mod tests {
385448    } 
386449
387450    proptest !  { 
451+         #[ test] 
452+         fn  test_sinpi( x:  f64 )  { 
453+             if  !x. is_finite( )  { 
454+                 return  Ok ( ( ) ) ; 
455+             } 
456+             eprintln!( "x = {x}" ) ; 
457+ 
458+             pyo3:: prepare_freethreaded_python( ) ; 
459+             Python :: with_gil( |py| { 
460+                 // Create Python function for comparing sinpi 
461+                 let  py_code = PyModule :: from_code( 
462+                     py, 
463+                     c"import math\n def sinpi(x): return math.sin(math.pi * x)" , 
464+                     c"" , 
465+                     c"" , 
466+                 ) 
467+                 . unwrap( ) ; 
468+ 
469+                 // Get results from both implementations 
470+                 let  rs_sinpi = m_sinpi( x) ; 
471+                 let  py_sinpi = py_code
472+                     . getattr( "sinpi" ) 
473+                     . unwrap( ) 
474+                     . call1( ( x, ) ) 
475+                     . unwrap( ) 
476+                     . extract:: <f64 >( ) 
477+                     . unwrap( ) ; 
478+ 
479+                 // Check if they're close enough 
480+                 // Get bit representation for detailed comparison 
481+                 let  rs_bits = unsafe  {  std:: mem:: transmute:: <f64 ,  i64 >( rs_sinpi)  } ; 
482+                 let  py_bits = unsafe  {  std:: mem:: transmute:: <f64 ,  i64 >( py_sinpi)  } ; 
483+                 assert_eq!( rs_bits,  py_bits) ; 
484+             } ) ; 
485+         } 
486+ 
388487        #[ test] 
389488        fn  test_tgamma( x:  f64 )  { 
390489            let  rs_gamma = tgamma( x) ; 
0 commit comments