Skip to content

Commit de90145

Browse files
Aadish JainAadish Jain
authored andcommitted
feat(binomial-cdf): adding all required binomial cdf functionality
1 parent 3ea906b commit de90145

File tree

19 files changed

+1570
-26
lines changed

19 files changed

+1570
-26
lines changed

lib/node_modules/@stdlib/math/base/napi/ternary/include/stdlib/math/base/napi/ternary.h

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -144,6 +144,48 @@
144144
}; \
145145
NAPI_MODULE( NODE_GYP_MODULE_NAME, stdlib_math_base_napi_dii_d_init )
146146

147+
/**
148+
* Macro for registering a Node-API module exporting an interface invoking a ternary function accepting a double-precision floating-point number and two signed 64-bit integers and returning a double-precision floating-point number.
149+
*
150+
* @param fcn ternary function
151+
*
152+
* @example
153+
* #include <stdint.h>
154+
*
155+
* static double fcn( const int_64 x, const int_64 y, const double z ) {
156+
* // ...
157+
* }
158+
*
159+
* // ...
160+
*
161+
* // Register a Node-API module:
162+
* STDLIB_MATH_BASE_NAPI_MODULE_LLD_D( fcn );
163+
*/
164+
#define STDLIB_MATH_BASE_NAPI_MODULE_LLD_D( fcn ) \
165+
static napi_value stdlib_math_base_napi_lld_d_wrapper( \
166+
napi_env env, \
167+
napi_callback_info info \
168+
) { \
169+
return stdlib_math_base_napi_lld_d( env, info, fcn ); \
170+
}; \
171+
static napi_value stdlib_math_base_napi_lld_d_init( \
172+
napi_env env, \
173+
napi_value exports \
174+
) { \
175+
napi_value fcn; \
176+
napi_status status = napi_create_function( \
177+
env, \
178+
"exports", \
179+
NAPI_AUTO_LENGTH, \
180+
stdlib_math_base_napi_lld_d_wrapper, \
181+
NULL, \
182+
&fcn \
183+
); \
184+
assert( status == napi_ok ); \
185+
return fcn; \
186+
}; \
187+
NAPI_MODULE( NODE_GYP_MODULE_NAME, stdlib_math_base_napi_lld_d_init )
188+
147189
/*
148190
* If C++, prevent name mangling so that the compiler emits a ternary file having undecorated names, thus mirroring the behavior of a C compiler.
149191
*/
@@ -166,6 +208,11 @@ napi_value stdlib_math_base_napi_fff_f( napi_env env, napi_callback_info info, f
166208
*/
167209
napi_value stdlib_math_base_napi_dii_d( napi_env env, napi_callback_info info, double (*fcn)( double, int32_t, int32_t ) );
168210

211+
/**
212+
* Invokes a ternary function accepting a double-precision floating-point number and two signed 64-bit integers and returning a double-precision floating-point number.
213+
*/
214+
napi_value stdlib_math_base_napi_lld_d( napi_env env, napi_callback_info info, double ( *fcn )( int64_t, int64_t, double ) );
215+
169216
#ifdef __cplusplus
170217
}
171218
#endif

lib/node_modules/@stdlib/math/base/napi/ternary/src/main.c

Lines changed: 76 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -248,3 +248,79 @@ napi_value stdlib_math_base_napi_dii_d( napi_env env, napi_callback_info info, d
248248

249249
return v;
250250
}
251+
252+
/**
253+
* Invokes a ternary function accepting a double-precision floating-point number and two signed 64-bit integers and returning a double-precision floating-point number.
254+
*
255+
* ## Notes
256+
*
257+
* - This function expects that the callback `info` argument provides access to the following JavaScript arguments:
258+
*
259+
* - `x`: input value.
260+
* - `y`: input value.
261+
* - `z`: input value.
262+
*
263+
* @param env environment under which the function is invoked
264+
* @param info callback data
265+
* @param fcn ternary function
266+
* @return function return value as a Node-API double-precision floating-point number
267+
*/
268+
napi_value stdlib_math_base_napi_lld_d( napi_env env, napi_callback_info info, double ( *fcn )( int64_t, int64_t, double ) ) {
269+
napi_status status;
270+
271+
size_t argc = 3;
272+
napi_value argv[ 3 ];
273+
status = napi_get_cb_info( env, info, &argc, argv, NULL, NULL );
274+
assert( status == napi_ok );
275+
276+
if ( argc < 3 ) {
277+
status = napi_throw_error( env, NULL, "invalid invocation. Must provide three numbers." );
278+
assert( status == napi_ok );
279+
return NULL;
280+
}
281+
282+
napi_valuetype vtype0;
283+
status = napi_typeof( env, argv[ 0 ], &vtype0 );
284+
assert( status == napi_ok );
285+
if ( vtype0 != napi_number ) {
286+
status = napi_throw_type_error( env, NULL, "invalid argument. First argument must be a number." );
287+
assert( status == napi_ok );
288+
return NULL;
289+
}
290+
291+
napi_valuetype vtype1;
292+
status = napi_typeof( env, argv[ 1 ], &vtype1 );
293+
assert( status == napi_ok );
294+
if ( vtype1 != napi_number ) {
295+
status = napi_throw_type_error( env, NULL, "invalid argument. Second argument must be a number." );
296+
assert( status == napi_ok );
297+
return NULL;
298+
}
299+
300+
napi_valuetype vtype2;
301+
status = napi_typeof( env, argv[ 2 ], &vtype2 );
302+
assert( status == napi_ok );
303+
if ( vtype2 != napi_number ) {
304+
status = napi_throw_type_error( env, NULL, "invalid argument. Third argument must be a number." );
305+
assert( status == napi_ok );
306+
return NULL;
307+
}
308+
309+
int64_t x;
310+
status = napi_get_value_int64( env, argv[ 0 ], &x );
311+
assert( status == napi_ok );
312+
313+
int64_t y;
314+
status = napi_get_value_int64( env, argv[ 1 ], &y );
315+
assert( status == napi_ok );
316+
317+
double z;
318+
status = napi_get_value_double( env, argv[ 2 ], &z );
319+
assert( status == napi_ok );
320+
321+
napi_value v;
322+
status = napi_create_double( env, fcn( x, y, z ), &v );
323+
assert( status == napi_ok );
324+
325+
return v;
326+
}

lib/node_modules/@stdlib/stats/base/dists/binomial/cdf/README.md

Lines changed: 97 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -167,6 +167,103 @@ for ( i = 0; i < 10; i++ ) {
167167

168168
<!-- /.examples -->
169169

170+
<!-- C interface documentation. -->
171+
172+
* * *
173+
174+
<section class="c">
175+
176+
## C APIs
177+
178+
<!-- Section to include introductory text. Make sure to keep an empty line after the intro `section` element and another before the `/section` close. -->
179+
180+
<section class="intro">
181+
182+
</section>
183+
184+
<!-- /.intro -->
185+
186+
<!-- C usage documentation. -->
187+
188+
<section class="usage">
189+
190+
### Usage
191+
192+
```c
193+
#include "stdlib/stats/base/dists/binomial/cdf.h"
194+
```
195+
196+
#### stdlib_base_dists_binomial_cdf( k, n, p )
197+
198+
Evaluates the cumulative distribution function (CDF) for a binomial distribution.
199+
200+
```c
201+
double out = stdlib_base_dists_binomial_cdf( 5, 10, 0.5 );
202+
// returns ~0.623
203+
```
204+
205+
The function accepts the following arguments:
206+
207+
- **k**: `[in] int` input value.
208+
- **n**: `[in] int` number of trials.
209+
- **p**: `[in] double` success probability.
210+
211+
```c
212+
double stdlib_base_dists_binomial_cdf( const int64_t k, const int64_t n, const double p );
213+
```
214+
215+
</section>
216+
<!-- /.usage -->
217+
218+
<!-- C API usage notes. Make sure to keep an empty line after the `section` element and another before the `/section` close. -->
219+
220+
<section class="notes">
221+
222+
</section>
223+
224+
<!-- /.notes -->
225+
226+
<!-- C API usage examples. -->
227+
228+
<section class="examples">
229+
### Examples
230+
231+
```c
232+
#include "stdlib/stats/base/dists/binomial/cdf.h"
233+
#include <stdlib.h>
234+
#include <stdio.h>
235+
#include <stdint.h>
236+
237+
static double random_uniform( const double min, const double max ) {
238+
double v = (double)rand() / ( (double)RAND_MAX + 1.0 );
239+
return min + ( v*(max-min) );
240+
}
241+
242+
int main( void ) {
243+
int64_t k;
244+
int64_t n;
245+
double p;
246+
double y;
247+
int i;
248+
249+
for ( i = 0; i < 25; i++ ) {
250+
k = (int64_t)random_uniform(0.0,10.0); // Random integer between 0 and 10
251+
n = k+(int64_t)random_uniform(0.0,10.0); // Random integer between k and 20
252+
p = random_uniform(0.0,1.0); // Random double between 0.0 and 1.0
253+
y = stdlib_base_dists_binomial_cdf( k, n, p );
254+
printf( "k: %d, n: %d, p: %lf, F(k;n,p): %lf\n", k, n, p, y );
255+
}
256+
}
257+
```
258+
259+
</section>
260+
261+
<!-- /.examples -->
262+
263+
</section>
264+
265+
<!-- /.c -->
266+
170267
<!-- Section for related `stdlib` packages. Do not manually edit this section, as it is automatically populated. -->
171268

172269
<section class="related">

lib/node_modules/@stdlib/stats/base/dists/binomial/cdf/benchmark/benchmark.js

Lines changed: 36 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -21,64 +21,74 @@
2121
// MODULES //
2222

2323
var bench = require( '@stdlib/bench' );
24-
var ceil = require( '@stdlib/math/base/special/ceil' );
24+
var Float64Array = require( '@stdlib/array/float64' );
25+
var uniform = require( '@stdlib/random/array/uniform' );
2526
var randu = require( '@stdlib/random/base/randu' );
27+
var floor = require( '@stdlib/math/base/special/floor' );
2628
var isnan = require( '@stdlib/math/base/assert/is-nan' );
2729
var pkg = require( './../package.json' ).name;
2830
var cdf = require( './../lib' );
2931

3032

3133
// MAIN //
3234

33-
bench( pkg, function benchmark( b ) {
35+
bench(pkg, function benchmark(b) {
36+
var len;
37+
var k;
3438
var n;
3539
var p;
36-
var x;
3740
var y;
3841
var i;
3942

43+
len = 100;
44+
k = new Float64Array(len);
45+
n = new Float64Array(len);
46+
p = new Float64Array(len);
47+
for (i = 0; i < len; i++) {
48+
k[i] = floor(randu() * 11);
49+
n[i] = floor(randu() * 21);
50+
p[i] = randu();
51+
}
52+
4053
b.tic();
41-
for ( i = 0; i < b.iterations; i++ ) {
42-
x = randu() * 100.0;
43-
n = ceil( randu()*100.0 );
44-
p = randu();
45-
y = cdf( x, n, p );
46-
if ( isnan( y ) ) {
47-
b.fail( 'should not return NaN' );
54+
for (i = 0; i < b.iterations; i++) {
55+
y = cdf(k[i % len], n[i % len], p[i % len]);
56+
if (isnan(y)) {
57+
b.fail('should not return NaN');
4858
}
4959
}
5060
b.toc();
51-
if ( isnan( y ) ) {
52-
b.fail( 'should not return NaN' );
61+
if (isnan(y)) {
62+
b.fail('should not return NaN');
5363
}
54-
b.pass( 'benchmark finished' );
64+
b.pass('benchmark finished');
5565
b.end();
5666
});
5767

58-
bench( pkg+':factory', function benchmark( b ) {
68+
bench(pkg + ':factory', function benchmark(b) {
5969
var mycdf;
6070
var n;
6171
var p;
62-
var x;
72+
var k;
6373
var y;
6474
var i;
6575

66-
n = 80;
67-
p = 0.4;
68-
mycdf = cdf.factory( n, p );
76+
n = 10;
77+
p = 0.5;
78+
mycdf = cdf.factory(n, p);
79+
k = uniform(100, 0, n);
6980

7081
b.tic();
71-
for ( i = 0; i < b.iterations; i++ ) {
72-
x = randu() * 80.0;
73-
y = mycdf( x );
74-
if ( isnan( y ) ) {
75-
b.fail( 'should not return NaN' );
82+
for (i = 0; i < b.iterations; i++) {
83+
y = mycdf(k[i % k.length]);
84+
if (isnan(y)) {
85+
b.fail('should not return NaN');
7686
}
7787
}
7888
b.toc();
79-
if ( isnan( y ) ) {
80-
b.fail( 'should not return NaN' );
89+
if (isnan(y)) {
90+
b.fail('should not return NaN');
8191
}
82-
b.pass( 'benchmark finished' );
92+
b.pass('benchmark finished');
8393
b.end();
8494
});

0 commit comments

Comments
 (0)