Coverage Report

Created: 2026-10-28 06:40

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/r-source/src/nmath/cospi.c
Line
Count
Source
1
/*
2
 *  Mathlib : A C Library of Special Functions
3
 *  Copyright (C) 2013-2022 The R Core Team
4
 *
5
 *  This program is free software; you can redistribute it and/or modify
6
 *  it under the terms of the GNU General Public License as published by
7
 *  the Free Software Foundation; either version 2 of the License, or
8
 *  (at your option) any later version.
9
 *
10
 *  This program is distributed in the hope that it will be useful,
11
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
12
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
 *  GNU General Public License for more details.
14
 */
15
16
#include "nmath.h"
17
18
/* HAVE_COSPI etc will not be defined in standalone-use: the
19
   intention is to make the versions here available in that case.
20
21
   The __cospi etc variants are from macOS (and perhaps other BSD-based systems).
22
*/
23
24
#ifdef HAVE_COSPI
25
#elif defined HAVE___COSPI
26
double cospi(double x) {
27
    return __cospi(x);
28
}
29
#else
30
// cos(pi * x)  -- exact when x = k/2  for all integer k
31
0
double cospi(double x) {
32
0
#ifdef IEEE_754
33
    /* NaNs propagated correctly */
34
0
    if (ISNAN(x)) return x;
35
0
#endif
36
0
    if(!R_FINITE(x)) ML_WARN_return_NAN;
37
38
0
    x = fmod(fabs(x), 2.);// cos() symmetric; cos(pi(x + 2k)) == cos(pi x) for all integer k
39
0
    if(fmod(x, 1.) == 0.5) return 0.;
40
0
    if( x == 1.) return -1.;
41
0
    if( x == 0.) return  1.;
42
    // otherwise
43
0
    return cos(M_PI * x);
44
0
}
45
#endif
46
47
#ifdef HAVE_SINPI
48
#elif defined HAVE___SINPI
49
double sinpi(double x) {
50
    return __sinpi(x);
51
}
52
#else
53
// sin(pi * x)  -- exact when x = k/2  for all integer k
54
0
double sinpi(double x) {
55
0
#ifdef IEEE_754
56
0
    if (ISNAN(x)) return x;
57
0
#endif
58
0
    if(!R_FINITE(x)) ML_WARN_return_NAN;
59
60
0
    x = fmod(x, 2.); // sin(pi(x + 2k)) == sin(pi x)  for all integer k
61
    // map (-2,2) --> (-1,1] :
62
0
    if(x <= -1) x += 2.; else if (x > 1.) x -= 2.;
63
0
    if(x == 0. || x == 1.) return 0.;
64
0
    if(x ==  0.5) return  1.;
65
0
    if(x == -0.5) return -1.;
66
    // otherwise
67
0
    return sin(M_PI * x);
68
0
}
69
#endif
70
71
// tan(pi * x)  -- exact when x = k/4  for all integer k and half-values give NaN
72
// ----------- e.g. used in ../main/arithmetic.c : 
73
double Rtanpi(double x)
74
0
{
75
0
#ifdef IEEE_754
76
0
    if (ISNAN(x)) return x;
77
0
#endif
78
0
    if(!R_FINITE(x)) ML_WARN_return_NAN;
79
80
0
    x = fmod(x, 1.); // tan(pi(x + k)) == tan(pi x)  for all integer k
81
    // map (-1,1] --> (-1/2, 1/2] :
82
0
    if(x <= -0.5) x++; else if(x > 0.5) x--;
83
0
    return (x == 0.) ? 0. :
84
0
  ((x ==  0.5 ) ? ML_NAN :
85
0
  ((x ==  0.25) ?  1. :
86
0
  ((x == -0.25) ? -1. :
87
0
      tan(M_PI * x)
88
0
      )));
89
0
}
90
91
#if defined(HAVE_TANPI) || defined(HAVE___TANPI)
92
#else
93
0
double tanpi(double x) {
94
0
    return Rtanpi(x);
95
0
}
96
#endif
97
98
#if !defined(HAVE_TANPI) && defined(HAVE___TANPI)
99
double tanpi(double x) {
100
    return __tanpi(x);
101
}
102
/* #else tanpi() defined from C standard math lib */
103
#endif