From f1e9bbdef719e08043629e9921f5d12dc5129f10 Mon Sep 17 00:00:00 2001 From: stdlib-bot <noreply@stdlib.io> Date: Tue, 24 Sep 2024 07:36:12 +0000 Subject: [PATCH] Auto-generated commit --- .github/.keepalive | 1 - CHANGELOG.md | 44 ++++++++++++++++ CONTRIBUTORS | 8 +++ README.md | 30 ++++++++++- benchmark/c/benchmark.length.c | 44 +++++++++++++++- dist/index.js | 14 ++--- dist/index.js.map | 8 +-- docs/repl.txt | 2 +- examples/c/example.c | 6 +++ include/stdlib/blas/base/dasum.h | 5 ++ lib/dasum.js | 43 ++------------- lib/dasum.native.js | 2 +- lib/ndarray.js | 29 +--------- lib/ndarray.native.js | 14 ++--- manifest.json | 90 +++++++++++++++++++++++--------- package.json | 4 +- src/addon.c | 27 ++++++++-- src/dasum.c | 38 ++------------ src/dasum_cblas.c | 29 ++++++++-- src/dasum_f.c | 35 +++++++++++-- src/dasum_ndarray.c | 71 +++++++++++++++++++++++++ test/test.dasum.js | 16 ++++-- test/test.dasum.native.js | 16 ++++-- test/test.ndarray.js | 2 +- test/test.ndarray.native.js | 2 +- 25 files changed, 406 insertions(+), 174 deletions(-) delete mode 100644 .github/.keepalive create mode 100644 src/dasum_ndarray.c diff --git a/.github/.keepalive b/.github/.keepalive deleted file mode 100644 index 513aa18..0000000 --- a/.github/.keepalive +++ /dev/null @@ -1 +0,0 @@ -2024-09-01T04:26:03.283Z diff --git a/CHANGELOG.md b/CHANGELOG.md index 82b5fbf..e4234ba 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,50 @@ > Package changelog. +<section class="release" id="unreleased"> + +## Unreleased (2024-09-24) + +<section class="features"> + +### Features + +- [`126c898`](https://github.com/stdlib-js/stdlib/commit/126c89855ae2df8c6db72ca48e138f6b45a179b0) - refactor JavaScript implementation and add C `ndarray` implementation for `blas/base/dasum` [(#2942)](https://github.com/stdlib-js/stdlib/pull/2942) + +</section> + +<!-- /.features --> + +<section class="commits"> + +### Commits + +<details> + +- [`126c898`](https://github.com/stdlib-js/stdlib/commit/126c89855ae2df8c6db72ca48e138f6b45a179b0) - **feat:** refactor JavaScript implementation and add C `ndarray` implementation for `blas/base/dasum` [(#2942)](https://github.com/stdlib-js/stdlib/pull/2942) _(by Aman Bhansali)_ + +</details> + +</section> + +<!-- /.commits --> + +<section class="contributors"> + +### Contributors + +A total of 1 person contributed to this release. Thank you to this contributor: + +- Aman Bhansali + +</section> + +<!-- /.contributors --> + +</section> + +<!-- /.release --> + <section class="release" id="v0.3.0"> ## 0.3.0 (2024-07-28) diff --git a/CONTRIBUTORS b/CONTRIBUTORS index 57d1184..3a0c547 100644 --- a/CONTRIBUTORS +++ b/CONTRIBUTORS @@ -2,6 +2,7 @@ # # Contributors listed in alphabetical order. +Aayush Khanna <96649223+aayush0325@users.noreply.github.com> Adarsh Palaskar <adarshpalaskar99@gmail.com> Aditya Sapra <adityaework@gmail.com> AgPriyanshu18 <113460573+AgPriyanshu18@users.noreply.github.com> @@ -26,17 +27,20 @@ EuniceSim142 <77243938+EuniceSim142@users.noreply.github.com> Frank Kovacs <fran70kk@gmail.com> Golden Kumar <103646877+AuenKr@users.noreply.github.com> Gunj Joshi <gunjjoshi8372@gmail.com> +HarshaNP <96897754+GittyHarsha@users.noreply.github.com> Harshita Kalani <harshitakalani02@gmail.com> Hridyanshu <124202756+HRIDYANSHU054@users.noreply.github.com> Jaimin Godhani <112328542+Jai0401@users.noreply.github.com> James Gelok <jdgelok@gmail.com> Jaysukh Makvana <jaysukhmakvana2004@gmail.com> +Jenish Thapa <141203631+jenish-thapa@users.noreply.github.com> Jithin KS <jithinks112@gmail.com> Joel Mathew Koshy <joelmathewkoshy@gmail.com> Joey Reed <joeyrreed@gmail.com> Jordan Gallivan <115050475+Jordan-Gallivan@users.noreply.github.com> Joris Labie <joris.labie1@gmail.com> Justin Dennison <justin1dennison@gmail.com> +Kaif Mohd <mdkaifprofession@gmail.com> Karthik Prakash <116057817+skoriop@users.noreply.github.com> Khaldon <kahmd1444@gmail.com> Krishnendu Das <86651039+itskdhere@users.noreply.github.com> @@ -86,13 +90,17 @@ Stephannie Jiménez Gacha <steff456@hotmail.com> Suraj kumar <125961509+kumarsuraj212003@users.noreply.github.com> Tirtadwipa Manunggal <tirtadwipa.manunggal@gmail.com> Tudor Pagu <104032457+tudor-pagu@users.noreply.github.com> +Tufailahmed Bargir <142114244+Tufailahmed-Bargir@users.noreply.github.com> Utkarsh <http://utkarsh11105@gmail.com> Utkarsh Raj <rajutkarsh2505@gmail.com> +Vaibhav Patel <98279986+noobCoderVP@users.noreply.github.com> Varad Gupta <varadgupta21@gmail.com> Xiaochuan Ye <tap91624@gmail.com> Yernar Yergaziyev <yernar.yergaziyev@erg.kz> naveen <stupiddint@gmail.com> nishant-s7 <97207366+nishant-s7@users.noreply.github.com> +olenkabilonizhka <62379231+olenkabilonizhka@users.noreply.github.com> orimiles5 <97595296+orimiles5@users.noreply.github.com> rainn <88160429+AmCodesLame@users.noreply.github.com> rei2hu <reimu@reimu.ws> +yaswanth <116426380+yaswanthkosuru@users.noreply.github.com> diff --git a/README.md b/README.md index b7ecbe6..2afcee5 100644 --- a/README.md +++ b/README.md @@ -130,7 +130,7 @@ var sum = dasum( 3, x1, 2 ); // returns 12.0 ``` -If either `N` or `stride` is less than or equal to `0`, the function returns `0`. +If `N` is less than or equal to `0`, the function returns `0`. #### dasum.ndarray( N, x, stride, offset ) @@ -250,6 +250,28 @@ The function accepts the following arguments: double c_dasum( const CBLAS_INT N, const double *X, const CBLAS_INT stride ); ``` +#### c_dasum_ndarray( N, \*X, stride, offset ) + +Computes the sum of absolute values using alternative indexing semantics. + +```c +const double x[] = { 1.0, 2.0, 3.0, 4.0 }; + +double v = c_dasum_ndarray( 4, x, -1, 3 ); +// returns 10.0 +``` + +The function accepts the following arguments: + +- **N**: `[in] CBLAS_INT` number of indexed elements. +- **X**: `[in] double*` input array. +- **stride**: `[in] CBLAS_INT` index increment for `X`. +- **offset**: `[in] CBLAS_INT` starting index for `X`. + +```c +double c_dasum_ndarray( const CBLAS_INT N, const double *X, const CBLAS_INT stride, const CBLAS_INT offset ); +``` + </section> <!-- /.usage --> @@ -287,6 +309,12 @@ int main( void ) { // Print the result: printf( "sum: %lf\n", sum ); + + // Compute the sum of absolute values: + sum = c_dasum_ndarray( N, x, -strideX, N-1 ); + + // Print the result: + printf( "sum: %lf\n", sum ); } ``` diff --git a/benchmark/c/benchmark.length.c b/benchmark/c/benchmark.length.c index 4bf10db..ec801fd 100644 --- a/benchmark/c/benchmark.length.c +++ b/benchmark/c/benchmark.length.c @@ -94,7 +94,7 @@ static double rand_double( void ) { * @param len array length * @return elapsed time in seconds */ -static double benchmark( int iterations, int len ) { +static double benchmark1( int iterations, int len ) { double elapsed; double x[ len ]; double y; @@ -120,6 +120,39 @@ static double benchmark( int iterations, int len ) { return elapsed; } +/** +* Runs a benchmark. +* +* @param iterations number of iterations +* @param len array length +* @return elapsed time in seconds +*/ +static double benchmark2( int iterations, int len ) { + double elapsed; + double x[ len ]; + double y; + double t; + int i; + + for ( i = 0; i < len; i++ ) { + x[ i ] = ( rand_double()*20000.0 ) - 10000.0; + } + y = 0.0; + t = tic(); + for ( i = 0; i < iterations; i++ ) { + y = c_dasum_ndarray( len, x, 1, 0 ); + if ( y != y ) { + printf( "should not return NaN\n" ); + break; + } + } + elapsed = tic() - t; + if ( y != y ) { + printf( "should not return NaN\n" ); + } + return elapsed; +} + /** * Main execution sequence. */ @@ -142,7 +175,14 @@ int main( void ) { for ( j = 0; j < REPEATS; j++ ) { count += 1; printf( "# c::%s:len=%d\n", NAME, len ); - elapsed = benchmark( iter, len ); + elapsed = benchmark1( iter, len ); + print_results( iter, elapsed ); + printf( "ok %d benchmark finished\n", count ); + } + for ( j = 0; j < REPEATS; j++ ) { + count += 1; + printf( "# c::%s:ndarray:len=%d\n", NAME, len ); + elapsed = benchmark2( iter, len ); print_results( iter, elapsed ); printf( "ok %d benchmark finished\n", count ); } diff --git a/dist/index.js b/dist/index.js index 0ae6228..25bfb8c 100644 --- a/dist/index.js +++ b/dist/index.js @@ -1,9 +1,9 @@ -"use strict";var m=function(a,e){return function(){return e||a((e={exports:{}}).exports,e),e.exports}};var y=m(function(B,p){ -var n=require('@stdlib/math-base-special-abs/dist'),q=6;function _(a,e,v){var i,u,r;if(i=0,a<=0||v<=0)return i;if(v===1){if(u=a%q,u>0)for(r=0;r<u;r++)i+=n(e[r]);if(a<q)return i;for(r=u;r<a;r+=q)i+=n(e[r])+n(e[r+1])+n(e[r+2])+n(e[r+3])+n(e[r+4])+n(e[r+5]);return i}for(a*=v,r=0;r<a;r+=v)i+=n(e[r]);return i}p.exports=_ -});var j=m(function(C,d){ -var s=require('@stdlib/math-base-special-abs/dist'),o=6;function E(a,e,v,i){var u,r,f,t;if(u=0,a<=0)return u;if(r=i,v===1){if(f=a%o,f>0)for(t=0;t<f;t++)u+=s(e[r]),r+=v;if(a<o)return u;for(t=f;t<a;t+=o)u+=s(e[r])+s(e[r+1])+s(e[r+2])+s(e[r+3])+s(e[r+4])+s(e[r+5]),r+=o;return u}for(t=0;t<a;t++)u+=s(e[r]),r+=v;return u}d.exports=E -});var M=m(function(D,l){ -var O=require('@stdlib/utils-define-nonenumerable-read-only-property/dist'),b=y(),g=j();O(b,"ndarray",g);l.exports=b -});var h=require("path").join,k=require('@stdlib/utils-try-require/dist'),w=require('@stdlib/assert-is-error/dist'),z=M(),c,R=k(h(__dirname,"./native.js"));w(R)?c=z:c=R;module.exports=c; +"use strict";var v=function(e,r){return function(){return r||e((r={exports:{}}).exports,r),r.exports}};var n=v(function(z,q){ +var y=require('@stdlib/math-base-special-abs/dist');function j(e,r,a,u){var i,s,t;if(i=0,e<=0)return i;for(s=u,t=0;t<e;t++)i+=y(r[s]),s+=a;return i}q.exports=j +});var m=v(function(A,d){ +var l=require('@stdlib/strided-base-stride2offset/dist'),R=n();function _(e,r,a){var u=l(e,a);return R(e,r,a,u)}d.exports=_ +});var x=v(function(B,c){ +var b=require('@stdlib/utils-define-nonenumerable-read-only-property/dist'),f=m(),E=n();b(f,"ndarray",E);c.exports=f +});var O=require("path").join,g=require('@stdlib/utils-try-require/dist'),h=require('@stdlib/assert-is-error/dist'),k=x(),o,p=g(O(__dirname,"./native.js"));h(p)?o=k:o=p;module.exports=o; /** @license Apache-2.0 */ //# sourceMappingURL=index.js.map diff --git a/dist/index.js.map b/dist/index.js.map index ba798d7..9f487e2 100644 --- a/dist/index.js.map +++ b/dist/index.js.map @@ -1,7 +1,7 @@ { "version": 3, - "sources": ["../lib/dasum.js", "../lib/ndarray.js", "../lib/main.js", "../lib/index.js"], - "sourcesContent": ["/**\n* @license Apache-2.0\n*\n* Copyright (c) 2018 The Stdlib Authors.\n*\n* Licensed under the Apache License, Version 2.0 (the \"License\");\n* you may not use this file except in compliance with the License.\n* You may obtain a copy of the License at\n*\n* http://www.apache.org/licenses/LICENSE-2.0\n*\n* Unless required by applicable law or agreed to in writing, software\n* distributed under the License is distributed on an \"AS IS\" BASIS,\n* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n* See the License for the specific language governing permissions and\n* limitations under the License.\n*/\n\n'use strict';\n\n// MODULES //\n\nvar abs = require( '@stdlib/math-base-special-abs' );\n\n\n// VARIABLES //\n\nvar M = 6;\n\n\n// MAIN //\n\n/**\n* Computes the sum of absolute values.\n*\n* @param {PositiveInteger} N - number of indexed elements\n* @param {Float64Array} x - input array\n* @param {PositiveInteger} stride - `x` stride length\n* @returns {number} sum\n*\n* @example\n* var Float64Array = require( '@stdlib/array-float64' );\n*\n* var x = new Float64Array( [ 1.0, -2.0, 3.0, -4.0, 5.0 ] );\n*\n* var s = dasum( x.length, x, 1 );\n* // returns 15.0\n*/\nfunction dasum( N, x, stride ) {\n\tvar sum;\n\tvar m;\n\tvar i;\n\n\tsum = 0.0;\n\tif ( N <= 0 || stride <= 0 ) {\n\t\treturn sum;\n\t}\n\t// Use unrolled loops if the stride is equal to `1`...\n\tif ( stride === 1 ) {\n\t\tm = N % M;\n\n\t\t// If we have a remainder, run a clean-up loop...\n\t\tif ( m > 0 ) {\n\t\t\tfor ( i = 0; i < m; i++ ) {\n\t\t\t\tsum += abs( x[i] );\n\t\t\t}\n\t\t}\n\t\tif ( N < M ) {\n\t\t\treturn sum;\n\t\t}\n\t\tfor ( i = m; i < N; i += M ) {\n\t\t\tsum += abs(x[i]) + abs(x[i+1]) + abs(x[i+2]) + abs(x[i+3]) + abs(x[i+4]) + abs(x[i+5]); // eslint-disable-line max-len\n\t\t}\n\t\treturn sum;\n\t}\n\tN *= stride;\n\tfor ( i = 0; i < N; i += stride ) {\n\t\tsum += abs( x[i] );\n\t}\n\treturn sum;\n}\n\n\n// EXPORTS //\n\nmodule.exports = dasum;\n", "/**\n* @license Apache-2.0\n*\n* Copyright (c) 2018 The Stdlib Authors.\n*\n* Licensed under the Apache License, Version 2.0 (the \"License\");\n* you may not use this file except in compliance with the License.\n* You may obtain a copy of the License at\n*\n* http://www.apache.org/licenses/LICENSE-2.0\n*\n* Unless required by applicable law or agreed to in writing, software\n* distributed under the License is distributed on an \"AS IS\" BASIS,\n* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n* See the License for the specific language governing permissions and\n* limitations under the License.\n*/\n\n'use strict';\n\n// MODULES //\n\nvar abs = require( '@stdlib/math-base-special-abs' );\n\n\n// VARIABLES //\n\nvar M = 6;\n\n\n// MAIN //\n\n/**\n* Computes the sum of absolute values.\n*\n* @param {PositiveInteger} N - number of indexed elements\n* @param {Float64Array} x - input array\n* @param {integer} stride - `x` stride length\n* @param {NonNegativeInteger} offset - starting `x` index\n* @returns {number} sum\n*\n* @example\n* var Float64Array = require( '@stdlib/array-float64' );\n*\n* var x = new Float64Array( [ 1.0, -2.0, 3.0, -4.0, 5.0 ] );\n*\n* var s = dasum( x.length, x, 1, 0 );\n* // returns 15.0\n*/\nfunction dasum( N, x, stride, offset ) {\n\tvar sum;\n\tvar ix;\n\tvar m;\n\tvar i;\n\n\tsum = 0.0;\n\tif ( N <= 0 ) {\n\t\treturn sum;\n\t}\n\tix = offset;\n\n\t// Use unrolled loops if the stride is equal to `1`...\n\tif ( stride === 1 ) {\n\t\tm = N % M;\n\n\t\t// If we have a remainder, run a clean-up loop...\n\t\tif ( m > 0 ) {\n\t\t\tfor ( i = 0; i < m; i++ ) {\n\t\t\t\tsum += abs( x[ix] );\n\t\t\t\tix += stride;\n\t\t\t}\n\t\t}\n\t\tif ( N < M ) {\n\t\t\treturn sum;\n\t\t}\n\t\tfor ( i = m; i < N; i += M ) {\n\t\t\tsum += abs( x[ix] ) + abs( x[ix+1] ) + abs( x[ix+2] ) + abs( x[ix+3] ) + abs( x[ix+4] ) + abs( x[ix+5] ); // eslint-disable-line max-len\n\t\t\tix += M;\n\t\t}\n\t\treturn sum;\n\t}\n\tfor ( i = 0; i < N; i++ ) {\n\t\tsum += abs( x[ix] );\n\t\tix += stride;\n\t}\n\treturn sum;\n}\n\n\n// EXPORTS //\n\nmodule.exports = dasum;\n", "/**\n* @license Apache-2.0\n*\n* Copyright (c) 2018 The Stdlib Authors.\n*\n* Licensed under the Apache License, Version 2.0 (the \"License\");\n* you may not use this file except in compliance with the License.\n* You may obtain a copy of the License at\n*\n* http://www.apache.org/licenses/LICENSE-2.0\n*\n* Unless required by applicable law or agreed to in writing, software\n* distributed under the License is distributed on an \"AS IS\" BASIS,\n* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n* See the License for the specific language governing permissions and\n* limitations under the License.\n*/\n\n'use strict';\n\n// MODULES //\n\nvar setReadOnly = require( '@stdlib/utils-define-nonenumerable-read-only-property' );\nvar dasum = require( './dasum.js' );\nvar ndarray = require( './ndarray.js' );\n\n\n// MAIN //\n\nsetReadOnly( dasum, 'ndarray', ndarray );\n\n\n// EXPORTS //\n\nmodule.exports = dasum;\n", "/**\n* @license Apache-2.0\n*\n* Copyright (c) 2018 The Stdlib Authors.\n*\n* Licensed under the Apache License, Version 2.0 (the \"License\");\n* you may not use this file except in compliance with the License.\n* You may obtain a copy of the License at\n*\n* http://www.apache.org/licenses/LICENSE-2.0\n*\n* Unless required by applicable law or agreed to in writing, software\n* distributed under the License is distributed on an \"AS IS\" BASIS,\n* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n* See the License for the specific language governing permissions and\n* limitations under the License.\n*/\n\n'use strict';\n\n/**\n* BLAS level 1 routine to compute the sum of absolute values.\n*\n* @module @stdlib/blas-base-dasum\n*\n* @example\n* var Float64Array = require( '@stdlib/array-float64' );\n* var dasum = require( '@stdlib/blas-base-dasum' );\n*\n* var x = new Float64Array( [ 1.0, -2.0, 3.0, -4.0, 5.0 ] );\n*\n* var s = dasum( x.length, x, 1 );\n* // returns 15.0\n*\n* @example\n* var Float64Array = require( '@stdlib/array-float64' );\n* var dasum = require( '@stdlib/blas-base-dasum' );\n*\n* var x = new Float64Array( [ 1.0, -2.0, 3.0, -4.0, 5.0 ] );\n*\n* var s = dasum.ndarray( x.length, x, 1, 0 );\n* // returns 15.0\n*/\n\n// MODULES //\n\nvar join = require( 'path' ).join;\nvar tryRequire = require( '@stdlib/utils-try-require' );\nvar isError = require( '@stdlib/assert-is-error' );\nvar main = require( './main.js' );\n\n\n// MAIN //\n\nvar dasum;\nvar tmp = tryRequire( join( __dirname, './native.js' ) );\nif ( isError( tmp ) ) {\n\tdasum = main;\n} else {\n\tdasum = tmp;\n}\n\n\n// EXPORTS //\n\nmodule.exports = dasum;\n\n// exports: { \"ndarray\": \"dasum.ndarray\" }\n"], - "mappings": "uGAAA,IAAAA,EAAAC,EAAA,SAAAC,EAAAC,EAAA,cAsBA,IAAIC,EAAM,QAAS,+BAAgC,EAK/CC,EAAI,EAqBR,SAASC,EAAOC,EAAGC,EAAGC,EAAS,CAC9B,IAAIC,EACAC,EACAC,EAGJ,GADAF,EAAM,EACDH,GAAK,GAAKE,GAAU,EACxB,OAAOC,EAGR,GAAKD,IAAW,EAAI,CAInB,GAHAE,EAAIJ,EAAIF,EAGHM,EAAI,EACR,IAAMC,EAAI,EAAGA,EAAID,EAAGC,IACnBF,GAAON,EAAKI,EAAEI,CAAC,CAAE,EAGnB,GAAKL,EAAIF,EACR,OAAOK,EAER,IAAME,EAAID,EAAGC,EAAIL,EAAGK,GAAKP,EACxBK,GAAON,EAAII,EAAEI,CAAC,CAAC,EAAIR,EAAII,EAAEI,EAAE,CAAC,CAAC,EAAIR,EAAII,EAAEI,EAAE,CAAC,CAAC,EAAIR,EAAII,EAAEI,EAAE,CAAC,CAAC,EAAIR,EAAII,EAAEI,EAAE,CAAC,CAAC,EAAIR,EAAII,EAAEI,EAAE,CAAC,CAAC,EAEtF,OAAOF,CACR,CAEA,IADAH,GAAKE,EACCG,EAAI,EAAGA,EAAIL,EAAGK,GAAKH,EACxBC,GAAON,EAAKI,EAAEI,CAAC,CAAE,EAElB,OAAOF,CACR,CAKAP,EAAO,QAAUG,ICrFjB,IAAAO,EAAAC,EAAA,SAAAC,EAAAC,EAAA,cAsBA,IAAIC,EAAM,QAAS,+BAAgC,EAK/CC,EAAI,EAsBR,SAASC,EAAOC,EAAGC,EAAGC,EAAQC,EAAS,CACtC,IAAIC,EACAC,EACAC,EACAC,EAGJ,GADAH,EAAM,EACDJ,GAAK,EACT,OAAOI,EAKR,GAHAC,EAAKF,EAGAD,IAAW,EAAI,CAInB,GAHAI,EAAIN,EAAIF,EAGHQ,EAAI,EACR,IAAMC,EAAI,EAAGA,EAAID,EAAGC,IACnBH,GAAOP,EAAKI,EAAEI,CAAE,CAAE,EAClBA,GAAMH,EAGR,GAAKF,EAAIF,EACR,OAAOM,EAER,IAAMG,EAAID,EAAGC,EAAIP,EAAGO,GAAKT,EACxBM,GAAOP,EAAKI,EAAEI,CAAE,CAAE,EAAIR,EAAKI,EAAEI,EAAG,CAAC,CAAE,EAAIR,EAAKI,EAAEI,EAAG,CAAC,CAAE,EAAIR,EAAKI,EAAEI,EAAG,CAAC,CAAE,EAAIR,EAAKI,EAAEI,EAAG,CAAC,CAAE,EAAIR,EAAKI,EAAEI,EAAG,CAAC,CAAE,EACvGA,GAAMP,EAEP,OAAOM,CACR,CACA,IAAMG,EAAI,EAAGA,EAAIP,EAAGO,IACnBH,GAAOP,EAAKI,EAAEI,CAAE,CAAE,EAClBA,GAAMH,EAEP,OAAOE,CACR,CAKAR,EAAO,QAAUG,IC3FjB,IAAAS,EAAAC,EAAA,SAAAC,EAAAC,EAAA,cAsBA,IAAIC,EAAc,QAAS,uDAAwD,EAC/EC,EAAQ,IACRC,EAAU,IAKdF,EAAaC,EAAO,UAAWC,CAAQ,EAKvCH,EAAO,QAAUE,ICYjB,IAAIE,EAAO,QAAS,MAAO,EAAE,KACzBC,EAAa,QAAS,2BAA4B,EAClDC,EAAU,QAAS,yBAA0B,EAC7CC,EAAO,IAKPC,EACAC,EAAMJ,EAAYD,EAAM,UAAW,aAAc,CAAE,EAClDE,EAASG,CAAI,EACjBD,EAAQD,EAERC,EAAQC,EAMT,OAAO,QAAUD", - "names": ["require_dasum", "__commonJSMin", "exports", "module", "abs", "M", "dasum", "N", "x", "stride", "sum", "m", "i", "require_ndarray", "__commonJSMin", "exports", "module", "abs", "M", "dasum", "N", "x", "stride", "offset", "sum", "ix", "m", "i", "require_main", "__commonJSMin", "exports", "module", "setReadOnly", "dasum", "ndarray", "join", "tryRequire", "isError", "main", "dasum", "tmp"] + "sources": ["../lib/ndarray.js", "../lib/dasum.js", "../lib/main.js", "../lib/index.js"], + "sourcesContent": ["/**\n* @license Apache-2.0\n*\n* Copyright (c) 2018 The Stdlib Authors.\n*\n* Licensed under the Apache License, Version 2.0 (the \"License\");\n* you may not use this file except in compliance with the License.\n* You may obtain a copy of the License at\n*\n* http://www.apache.org/licenses/LICENSE-2.0\n*\n* Unless required by applicable law or agreed to in writing, software\n* distributed under the License is distributed on an \"AS IS\" BASIS,\n* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n* See the License for the specific language governing permissions and\n* limitations under the License.\n*/\n\n'use strict';\n\n// MODULES //\n\nvar abs = require( '@stdlib/math-base-special-abs' );\n\n\n// MAIN //\n\n/**\n* Computes the sum of absolute values.\n*\n* @param {PositiveInteger} N - number of indexed elements\n* @param {Float64Array} x - input array\n* @param {integer} stride - `x` stride length\n* @param {NonNegativeInteger} offset - starting index for `x`\n* @returns {number} sum\n*\n* @example\n* var Float64Array = require( '@stdlib/array-float64' );\n*\n* var x = new Float64Array( [ 1.0, -2.0, 3.0, -4.0, 5.0 ] );\n*\n* var s = dasum( x.length, x, 1, 0 );\n* // returns 15.0\n*/\nfunction dasum( N, x, stride, offset ) {\n\tvar sum;\n\tvar ix;\n\tvar i;\n\n\tsum = 0.0;\n\tif ( N <= 0 ) {\n\t\treturn sum;\n\t}\n\tix = offset;\n\tfor ( i = 0; i < N; i++ ) {\n\t\tsum += abs( x[ix] );\n\t\tix += stride;\n\t}\n\treturn sum;\n}\n\n\n// EXPORTS //\n\nmodule.exports = dasum;\n", "/**\n* @license Apache-2.0\n*\n* Copyright (c) 2018 The Stdlib Authors.\n*\n* Licensed under the Apache License, Version 2.0 (the \"License\");\n* you may not use this file except in compliance with the License.\n* You may obtain a copy of the License at\n*\n* http://www.apache.org/licenses/LICENSE-2.0\n*\n* Unless required by applicable law or agreed to in writing, software\n* distributed under the License is distributed on an \"AS IS\" BASIS,\n* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n* See the License for the specific language governing permissions and\n* limitations under the License.\n*/\n\n'use strict';\n\n// MODULES //\n\nvar stride2offset = require( '@stdlib/strided-base-stride2offset' );\nvar ndarray = require( './ndarray.js' );\n\n\n// MAIN //\n\n/**\n* Computes the sum of absolute values.\n*\n* @param {PositiveInteger} N - number of indexed elements\n* @param {Float64Array} x - input array\n* @param {integer} stride - `x` stride length\n* @returns {number} sum\n*\n* @example\n* var Float64Array = require( '@stdlib/array-float64' );\n*\n* var x = new Float64Array( [ 1.0, -2.0, 3.0, -4.0, 5.0 ] );\n*\n* var s = dasum( x.length, x, 1 );\n* // returns 15.0\n*/\nfunction dasum( N, x, stride ) {\n\tvar ox = stride2offset( N, stride );\n\treturn ndarray( N, x, stride, ox );\n}\n\n\n// EXPORTS //\n\nmodule.exports = dasum;\n", "/**\n* @license Apache-2.0\n*\n* Copyright (c) 2018 The Stdlib Authors.\n*\n* Licensed under the Apache License, Version 2.0 (the \"License\");\n* you may not use this file except in compliance with the License.\n* You may obtain a copy of the License at\n*\n* http://www.apache.org/licenses/LICENSE-2.0\n*\n* Unless required by applicable law or agreed to in writing, software\n* distributed under the License is distributed on an \"AS IS\" BASIS,\n* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n* See the License for the specific language governing permissions and\n* limitations under the License.\n*/\n\n'use strict';\n\n// MODULES //\n\nvar setReadOnly = require( '@stdlib/utils-define-nonenumerable-read-only-property' );\nvar dasum = require( './dasum.js' );\nvar ndarray = require( './ndarray.js' );\n\n\n// MAIN //\n\nsetReadOnly( dasum, 'ndarray', ndarray );\n\n\n// EXPORTS //\n\nmodule.exports = dasum;\n", "/**\n* @license Apache-2.0\n*\n* Copyright (c) 2018 The Stdlib Authors.\n*\n* Licensed under the Apache License, Version 2.0 (the \"License\");\n* you may not use this file except in compliance with the License.\n* You may obtain a copy of the License at\n*\n* http://www.apache.org/licenses/LICENSE-2.0\n*\n* Unless required by applicable law or agreed to in writing, software\n* distributed under the License is distributed on an \"AS IS\" BASIS,\n* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n* See the License for the specific language governing permissions and\n* limitations under the License.\n*/\n\n'use strict';\n\n/**\n* BLAS level 1 routine to compute the sum of absolute values.\n*\n* @module @stdlib/blas-base-dasum\n*\n* @example\n* var Float64Array = require( '@stdlib/array-float64' );\n* var dasum = require( '@stdlib/blas-base-dasum' );\n*\n* var x = new Float64Array( [ 1.0, -2.0, 3.0, -4.0, 5.0 ] );\n*\n* var s = dasum( x.length, x, 1 );\n* // returns 15.0\n*\n* @example\n* var Float64Array = require( '@stdlib/array-float64' );\n* var dasum = require( '@stdlib/blas-base-dasum' );\n*\n* var x = new Float64Array( [ 1.0, -2.0, 3.0, -4.0, 5.0 ] );\n*\n* var s = dasum.ndarray( x.length, x, 1, 0 );\n* // returns 15.0\n*/\n\n// MODULES //\n\nvar join = require( 'path' ).join;\nvar tryRequire = require( '@stdlib/utils-try-require' );\nvar isError = require( '@stdlib/assert-is-error' );\nvar main = require( './main.js' );\n\n\n// MAIN //\n\nvar dasum;\nvar tmp = tryRequire( join( __dirname, './native.js' ) );\nif ( isError( tmp ) ) {\n\tdasum = main;\n} else {\n\tdasum = tmp;\n}\n\n\n// EXPORTS //\n\nmodule.exports = dasum;\n\n// exports: { \"ndarray\": \"dasum.ndarray\" }\n"], + "mappings": "uGAAA,IAAAA,EAAAC,EAAA,SAAAC,EAAAC,EAAA,cAsBA,IAAIC,EAAM,QAAS,+BAAgC,EAsBnD,SAASC,EAAOC,EAAGC,EAAGC,EAAQC,EAAS,CACtC,IAAIC,EACAC,EACAC,EAGJ,GADAF,EAAM,EACDJ,GAAK,EACT,OAAOI,EAGR,IADAC,EAAKF,EACCG,EAAI,EAAGA,EAAIN,EAAGM,IACnBF,GAAON,EAAKG,EAAEI,CAAE,CAAE,EAClBA,GAAMH,EAEP,OAAOE,CACR,CAKAP,EAAO,QAAUE,IChEjB,IAAAQ,EAAAC,EAAA,SAAAC,EAAAC,EAAA,cAsBA,IAAIC,EAAgB,QAAS,oCAAqC,EAC9DC,EAAU,IAqBd,SAASC,EAAOC,EAAGC,EAAGC,EAAS,CAC9B,IAAIC,EAAKN,EAAeG,EAAGE,CAAO,EAClC,OAAOJ,EAASE,EAAGC,EAAGC,EAAQC,CAAG,CAClC,CAKAP,EAAO,QAAUG,ICpDjB,IAAAK,EAAAC,EAAA,SAAAC,EAAAC,EAAA,cAsBA,IAAIC,EAAc,QAAS,uDAAwD,EAC/EC,EAAQ,IACRC,EAAU,IAKdF,EAAaC,EAAO,UAAWC,CAAQ,EAKvCH,EAAO,QAAUE,ICYjB,IAAIE,EAAO,QAAS,MAAO,EAAE,KACzBC,EAAa,QAAS,2BAA4B,EAClDC,EAAU,QAAS,yBAA0B,EAC7CC,EAAO,IAKPC,EACAC,EAAMJ,EAAYD,EAAM,UAAW,aAAc,CAAE,EAClDE,EAASG,CAAI,EACjBD,EAAQD,EAERC,EAAQC,EAMT,OAAO,QAAUD", + "names": ["require_ndarray", "__commonJSMin", "exports", "module", "abs", "dasum", "N", "x", "stride", "offset", "sum", "ix", "i", "require_dasum", "__commonJSMin", "exports", "module", "stride2offset", "ndarray", "dasum", "N", "x", "stride", "ox", "require_main", "__commonJSMin", "exports", "module", "setReadOnly", "dasum", "ndarray", "join", "tryRequire", "isError", "main", "dasum", "tmp"] } diff --git a/docs/repl.txt b/docs/repl.txt index 7074e95..a1dc7b8 100644 --- a/docs/repl.txt +++ b/docs/repl.txt @@ -10,7 +10,7 @@ Indexing is relative to the first index. To introduce an offset, use typed array views. - If `N` or `stride` is less than or equal to `0`, the function returns `0`. + If `N` is less than or equal to `0`, the function returns `0`. Parameters ---------- diff --git a/examples/c/example.c b/examples/c/example.c index 490764e..07ea828 100644 --- a/examples/c/example.c +++ b/examples/c/example.c @@ -34,4 +34,10 @@ int main( void ) { // Print the result: printf( "sum: %lf\n", sum ); + + // Compute the sum of absolute values: + sum = c_dasum_ndarray( N, x, -strideX, N-1 ); + + // Print the result: + printf( "sum: %lf\n", sum ); } diff --git a/include/stdlib/blas/base/dasum.h b/include/stdlib/blas/base/dasum.h index 861d600..edb2a7c 100644 --- a/include/stdlib/blas/base/dasum.h +++ b/include/stdlib/blas/base/dasum.h @@ -36,6 +36,11 @@ extern "C" { */ double API_SUFFIX(c_dasum)( const CBLAS_INT N, const double *X, const CBLAS_INT stride ); +/** +* Computes the sum of absolute values using alternative indexing semantics. +*/ +double API_SUFFIX(c_dasum_ndarray)( const CBLAS_INT N, const double *X, const CBLAS_INT stride, const CBLAS_INT offset ); + #ifdef __cplusplus } #endif diff --git a/lib/dasum.js b/lib/dasum.js index 86163f9..58385f0 100644 --- a/lib/dasum.js +++ b/lib/dasum.js @@ -20,12 +20,8 @@ // MODULES // -var abs = require( '@stdlib/math-base-special-abs' ); - - -// VARIABLES // - -var M = 6; +var stride2offset = require( '@stdlib/strided-base-stride2offset' ); +var ndarray = require( './ndarray.js' ); // MAIN // @@ -35,7 +31,7 @@ var M = 6; * * @param {PositiveInteger} N - number of indexed elements * @param {Float64Array} x - input array -* @param {PositiveInteger} stride - `x` stride length +* @param {integer} stride - `x` stride length * @returns {number} sum * * @example @@ -47,37 +43,8 @@ var M = 6; * // returns 15.0 */ function dasum( N, x, stride ) { - var sum; - var m; - var i; - - sum = 0.0; - if ( N <= 0 || stride <= 0 ) { - return sum; - } - // Use unrolled loops if the stride is equal to `1`... - if ( stride === 1 ) { - m = N % M; - - // If we have a remainder, run a clean-up loop... - if ( m > 0 ) { - for ( i = 0; i < m; i++ ) { - sum += abs( x[i] ); - } - } - if ( N < M ) { - return sum; - } - for ( i = m; i < N; i += M ) { - sum += abs(x[i]) + abs(x[i+1]) + abs(x[i+2]) + abs(x[i+3]) + abs(x[i+4]) + abs(x[i+5]); // eslint-disable-line max-len - } - return sum; - } - N *= stride; - for ( i = 0; i < N; i += stride ) { - sum += abs( x[i] ); - } - return sum; + var ox = stride2offset( N, stride ); + return ndarray( N, x, stride, ox ); } diff --git a/lib/dasum.native.js b/lib/dasum.native.js index 86b5d65..2a6f9ab 100644 --- a/lib/dasum.native.js +++ b/lib/dasum.native.js @@ -30,7 +30,7 @@ var addon = require( './../src/addon.node' ); * * @param {PositiveInteger} N - number of indexed elements * @param {Float64Array} x - input array -* @param {PositiveInteger} stride - `x` stride length +* @param {integer} stride - `x` stride length * @returns {number} sum * * @example diff --git a/lib/ndarray.js b/lib/ndarray.js index 3cd076c..217111c 100644 --- a/lib/ndarray.js +++ b/lib/ndarray.js @@ -23,11 +23,6 @@ var abs = require( '@stdlib/math-base-special-abs' ); -// VARIABLES // - -var M = 6; - - // MAIN // /** @@ -36,7 +31,7 @@ var M = 6; * @param {PositiveInteger} N - number of indexed elements * @param {Float64Array} x - input array * @param {integer} stride - `x` stride length -* @param {NonNegativeInteger} offset - starting `x` index +* @param {NonNegativeInteger} offset - starting index for `x` * @returns {number} sum * * @example @@ -50,7 +45,6 @@ var M = 6; function dasum( N, x, stride, offset ) { var sum; var ix; - var m; var i; sum = 0.0; @@ -58,27 +52,6 @@ function dasum( N, x, stride, offset ) { return sum; } ix = offset; - - // Use unrolled loops if the stride is equal to `1`... - if ( stride === 1 ) { - m = N % M; - - // If we have a remainder, run a clean-up loop... - if ( m > 0 ) { - for ( i = 0; i < m; i++ ) { - sum += abs( x[ix] ); - ix += stride; - } - } - if ( N < M ) { - return sum; - } - for ( i = m; i < N; i += M ) { - sum += abs( x[ix] ) + abs( x[ix+1] ) + abs( x[ix+2] ) + abs( x[ix+3] ) + abs( x[ix+4] ) + abs( x[ix+5] ); // eslint-disable-line max-len - ix += M; - } - return sum; - } for ( i = 0; i < N; i++ ) { sum += abs( x[ix] ); ix += stride; diff --git a/lib/ndarray.native.js b/lib/ndarray.native.js index 34607b8..9c803d3 100644 --- a/lib/ndarray.native.js +++ b/lib/ndarray.native.js @@ -20,9 +20,7 @@ // MODULES // -var minViewBufferIndex = require( '@stdlib/strided-base-min-view-buffer-index' ); -var offsetView = require( '@stdlib/strided-base-offset-view' ); -var addon = require( './dasum.native.js' ); +var addon = require( './../src/addon.node' ); // MAIN // @@ -33,7 +31,7 @@ var addon = require( './dasum.native.js' ); * @param {PositiveInteger} N - number of indexed elements * @param {Float64Array} x - input array * @param {integer} stride - `x` stride length -* @param {NonNegativeInteger} offset - starting `x` index +* @param {NonNegativeInteger} offset - starting index for `x` * @returns {number} sum * * @example @@ -45,13 +43,7 @@ var addon = require( './dasum.native.js' ); * // returns 15.0 */ function dasum( N, x, stride, offset ) { - var view; - offset = minViewBufferIndex( N, stride, offset ); - if ( stride < 0 ) { - stride *= -1; - } - view = offsetView( x, offset ); - return addon( N, view, stride ); + return addon.ndarray( N, x, stride, offset ); } diff --git a/manifest.json b/manifest.json index d6954d9..0f08a4e 100644 --- a/manifest.json +++ b/manifest.json @@ -45,6 +45,7 @@ "libpath": [], "dependencies": [ "@stdlib/blas-base-shared", + "@stdlib/strided-base-min-view-buffer-index", "@stdlib/napi-export", "@stdlib/napi-argv", "@stdlib/napi-argv-int64", @@ -58,15 +59,19 @@ "blas": "", "wasm": false, "src": [ - "./src/dasum.c" + "./src/dasum.c", + "./src/dasum_ndarray.c" ], "include": [ "./include" ], - "libraries": [], + "libraries": [ + "-lm" + ], "libpath": [], "dependencies": [ "@stdlib/blas-base-shared", + "@stdlib/strided-base-stride2offset", "@stdlib/math-base-special-abs" ] }, @@ -76,15 +81,19 @@ "blas": "", "wasm": false, "src": [ - "./src/dasum.c" + "./src/dasum.c", + "./src/dasum_ndarray.c" ], "include": [ "./include" ], - "libraries": [], + "libraries": [ + "-lm" + ], "libpath": [], "dependencies": [ "@stdlib/blas-base-shared", + "@stdlib/strided-base-stride2offset", "@stdlib/math-base-special-abs" ] }, @@ -107,6 +116,7 @@ "libpath": [], "dependencies": [ "@stdlib/blas-base-shared", + "@stdlib/strided-base-min-view-buffer-index", "@stdlib/napi-export", "@stdlib/napi-argv", "@stdlib/napi-argv-int64", @@ -131,7 +141,8 @@ ], "libpath": [], "dependencies": [ - "@stdlib/blas-base-shared" + "@stdlib/blas-base-shared", + "@stdlib/strided-base-min-view-buffer-index" ] }, { @@ -151,7 +162,8 @@ ], "libpath": [], "dependencies": [ - "@stdlib/blas-base-shared" + "@stdlib/blas-base-shared", + "@stdlib/strided-base-min-view-buffer-index" ] }, @@ -172,6 +184,7 @@ "libpath": [], "dependencies": [ "@stdlib/blas-base-shared", + "@stdlib/strided-base-min-view-buffer-index", "@stdlib/napi-export", "@stdlib/napi-argv", "@stdlib/napi-argv-int64", @@ -185,15 +198,19 @@ "blas": "", "wasm": false, "src": [ - "./src/dasum.c" + "./src/dasum.c", + "./src/dasum_ndarray.c" ], "include": [ "./include" ], - "libraries": [], + "libraries": [ + "-lm" + ], "libpath": [], "dependencies": [ "@stdlib/blas-base-shared", + "@stdlib/strided-base-stride2offset", "@stdlib/math-base-special-abs" ] }, @@ -203,15 +220,19 @@ "blas": "", "wasm": false, "src": [ - "./src/dasum.c" + "./src/dasum.c", + "./src/dasum_ndarray.c" ], "include": [ "./include" ], - "libraries": [], + "libraries": [ + "-lm" + ], "libpath": [], "dependencies": [ "@stdlib/blas-base-shared", + "@stdlib/strided-base-stride2offset", "@stdlib/math-base-special-abs" ] }, @@ -233,6 +254,7 @@ "libpath": [], "dependencies": [ "@stdlib/blas-base-shared", + "@stdlib/strided-base-min-view-buffer-index", "@stdlib/napi-export", "@stdlib/napi-argv", "@stdlib/napi-argv-int64", @@ -256,7 +278,8 @@ ], "libpath": [], "dependencies": [ - "@stdlib/blas-base-shared" + "@stdlib/blas-base-shared", + "@stdlib/strided-base-min-view-buffer-index" ] }, { @@ -275,7 +298,8 @@ ], "libpath": [], "dependencies": [ - "@stdlib/blas-base-shared" + "@stdlib/blas-base-shared", + "@stdlib/strided-base-min-view-buffer-index" ] }, @@ -297,6 +321,7 @@ "libpath": [], "dependencies": [ "@stdlib/blas-base-shared", + "@stdlib/strided-base-min-view-buffer-index", "@stdlib/napi-export", "@stdlib/napi-argv", "@stdlib/napi-argv-int64", @@ -321,7 +346,8 @@ ], "libpath": [], "dependencies": [ - "@stdlib/blas-base-shared" + "@stdlib/blas-base-shared", + "@stdlib/strided-base-min-view-buffer-index" ] }, { @@ -342,7 +368,7 @@ "libpath": [], "dependencies": [ "@stdlib/blas-base-shared", - "@stdlib/math-base-special-abs" + "@stdlib/strided-base-min-view-buffer-index" ] }, @@ -352,21 +378,25 @@ "blas": "", "wasm": false, "src": [ - "./src/dasum.c" + "./src/dasum.c", + "./src/dasum_ndarray.c" ], "include": [ "./include" ], - "libraries": [], + "libraries": [ + "-lm" + ], "libpath": [], "dependencies": [ "@stdlib/blas-base-shared", + "@stdlib/strided-base-stride2offset", + "@stdlib/math-base-special-abs", "@stdlib/napi-export", "@stdlib/napi-argv", "@stdlib/napi-argv-int64", "@stdlib/napi-argv-strided-float64array", - "@stdlib/napi-create-double", - "@stdlib/math-base-special-abs" + "@stdlib/napi-create-double" ] }, { @@ -375,15 +405,19 @@ "blas": "", "wasm": false, "src": [ - "./src/dasum.c" + "./src/dasum.c", + "./src/dasum_ndarray.c" ], "include": [ "./include" ], - "libraries": [], + "libraries": [ + "-lm" + ], "libpath": [], "dependencies": [ "@stdlib/blas-base-shared", + "@stdlib/strided-base-stride2offset", "@stdlib/math-base-special-abs" ] }, @@ -393,15 +427,19 @@ "blas": "", "wasm": false, "src": [ - "./src/dasum.c" + "./src/dasum.c", + "./src/dasum_ndarray.c" ], "include": [ "./include" ], - "libraries": [], + "libraries": [ + "-lm" + ], "libpath": [], "dependencies": [ "@stdlib/blas-base-shared", + "@stdlib/strided-base-stride2offset", "@stdlib/math-base-special-abs" ] }, @@ -412,15 +450,19 @@ "blas": "", "wasm": true, "src": [ - "./src/dasum.c" + "./src/dasum.c", + "./src/dasum_ndarray.c" ], "include": [ "./include" ], - "libraries": [], + "libraries": [ + "-lm" + ], "libpath": [], "dependencies": [ "@stdlib/blas-base-shared", + "@stdlib/strided-base-stride2offset", "@stdlib/math-base-special-abs" ] } diff --git a/package.json b/package.json index 8392a85..e07c92d 100644 --- a/package.json +++ b/package.json @@ -49,6 +49,8 @@ "@stdlib/napi-argv-strided-float64array": "^0.2.2", "@stdlib/napi-create-double": "^0.0.2", "@stdlib/napi-export": "^0.2.2", + "@stdlib/strided-base-min-view-buffer-index": "^0.2.2", + "@stdlib/strided-base-stride2offset": "^0.1.0", "@stdlib/utils-define-nonenumerable-read-only-property": "^0.2.2", "@stdlib/utils-library-manifest": "^0.2.2", "@stdlib/utils-try-require": "^0.2.2" @@ -61,8 +63,6 @@ "@stdlib/random-array-discrete-uniform": "^0.2.1", "@stdlib/random-array-uniform": "^0.2.1", "@stdlib/random-base-randu": "^0.2.1", - "@stdlib/strided-base-min-view-buffer-index": "^0.2.2", - "@stdlib/strided-base-offset-view": "^0.2.2", "proxyquire": "^2.0.0", "tape": "git+https://github.com/kgryte/tape.git#fix/globby", "istanbul": "^0.4.1", diff --git a/src/addon.c b/src/addon.c index 6d9deba..0fd3632 100644 --- a/src/addon.c +++ b/src/addon.c @@ -1,7 +1,7 @@ /** * @license Apache-2.0 * -* Copyright (c) 2018 The Stdlib Authors. +* Copyright (c) 2024 The Stdlib Authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -35,10 +35,27 @@ static napi_value addon( napi_env env, napi_callback_info info ) { STDLIB_NAPI_ARGV( env, info, argv, argc, 3 ); STDLIB_NAPI_ARGV_INT64( env, N, argv, 0 ); - STDLIB_NAPI_ARGV_INT64( env, strideX, argv, 2 ); - STDLIB_NAPI_ARGV_STRIDED_FLOAT64ARRAY( env, X, N, strideX, argv, 1 ); - STDLIB_NAPI_CREATE_DOUBLE( env, API_SUFFIX(c_dasum)( N, X, strideX ), v ); + STDLIB_NAPI_ARGV_INT64( env, stride, argv, 2 ); + STDLIB_NAPI_ARGV_STRIDED_FLOAT64ARRAY( env, X, N, stride, argv, 1 ); + STDLIB_NAPI_CREATE_DOUBLE( env, API_SUFFIX(c_dasum)( N, X, stride ), v ); return v; } -STDLIB_NAPI_MODULE_EXPORT_FCN( addon ) +/** +* Receives JavaScript callback invocation data. +* +* @param env environment under which the function is invoked +* @param info callback data +* @return Node-API value +*/ +static napi_value addon_method( napi_env env, napi_callback_info info ) { + STDLIB_NAPI_ARGV( env, info, argv, argc, 4 ); + STDLIB_NAPI_ARGV_INT64( env, N, argv, 0 ); + STDLIB_NAPI_ARGV_INT64( env, stride, argv, 2 ); + STDLIB_NAPI_ARGV_INT64( env, offset, argv, 3 ); + STDLIB_NAPI_ARGV_STRIDED_FLOAT64ARRAY( env, X, N, stride, argv, 1 ); + STDLIB_NAPI_CREATE_DOUBLE( env, API_SUFFIX(c_dasum_ndarray)( N, X, stride, offset ), v ); + return v; +} + +STDLIB_NAPI_MODULE_EXPORT_FCN_WITH_METHOD( addon, "ndarray", addon_method ) diff --git a/src/dasum.c b/src/dasum.c index e105688..dd93899 100644 --- a/src/dasum.c +++ b/src/dasum.c @@ -1,7 +1,7 @@ /** * @license Apache-2.0 * -* Copyright (c) 2018 The Stdlib Authors. +* Copyright (c) 2024 The Stdlib Authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -18,7 +18,7 @@ #include "stdlib/blas/base/dasum.h" #include "stdlib/blas/base/shared.h" -#include "stdlib/math/base/special/abs.h" +#include "stdlib/strided/base/stride2offset.h" /** * Computes the sum of absolute values. @@ -26,37 +26,9 @@ * @param N number of indexed elements * @param X input array * @param stride stride length -* @return sum of absolute values +* @return sum */ double API_SUFFIX(c_dasum)( const CBLAS_INT N, const double *X, const CBLAS_INT stride ) { - CBLAS_INT m; - CBLAS_INT i; - double sum; - - sum = 0.0; - if ( N <= 0 || stride <= 0 ) { - return sum; - } - // If the stride is equal to `1`, use unrolled loops... - if ( stride == 1 ) { - m = N % 6; - - // If we have a remainder, run a clean-up loop... - if ( m > 0 ) { - for ( i = 0; i < m; i++ ) { - sum += stdlib_base_abs( X[i] ); - } - } - if ( N < 6 ) { - return sum; - } - for ( i = m; i < N; i += 6 ) { - sum += stdlib_base_abs( X[i] ) + stdlib_base_abs( X[i+1] ) + stdlib_base_abs( X[i+2] ) + stdlib_base_abs( X[i+3] ) + stdlib_base_abs( X[i+4] ) + stdlib_base_abs( X[i+5] ); - } - return sum; - } - for ( i = 0; i < N*stride; i += stride ) { - sum += stdlib_base_abs( X[i] ); - } - return sum; + CBLAS_INT ox = stdlib_strided_stride2offset( N, stride ); + return API_SUFFIX(c_dasum_ndarray)( N, X, stride, ox ); } diff --git a/src/dasum_cblas.c b/src/dasum_cblas.c index 303cad6..52b25cb 100644 --- a/src/dasum_cblas.c +++ b/src/dasum_cblas.c @@ -1,7 +1,7 @@ /** * @license Apache-2.0 * -* Copyright (c) 2018 The Stdlib Authors. +* Copyright (c) 2024 The Stdlib Authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -19,6 +19,7 @@ #include "stdlib/blas/base/dasum.h" #include "stdlib/blas/base/dasum_cblas.h" #include "stdlib/blas/base/shared.h" +#include "stdlib/strided/base/min_view_buffer_index.h" /** * Computes the sum of absolute values. @@ -26,8 +27,30 @@ * @param N number of indexed elements * @param X input array * @param stride stride length -* @return sum of absolute values +* @return sum */ double API_SUFFIX(c_dasum)( const CBLAS_INT N, const double *X, const CBLAS_INT stride ) { - return API_SUFFIX(cblas_dasum)( N, X, stride ); + CBLAS_INT sx = stride; + if ( sx < 0 ) { + sx = -sx; + } + return API_SUFFIX(cblas_dasum)( N, X, sx ); +} + +/** +* Computes the sum of absolute values using alternative indexing semantics. +* +* @param N number of indexed elements +* @param X input array +* @param stride stride length +* @param offset starting index +* @return sum +*/ +double API_SUFFIX(c_dasum_ndarray)( const CBLAS_INT N, const double *X, const CBLAS_INT stride, const CBLAS_INT offset ) { + CBLAS_INT sx = stride; + if ( sx < 0 ) { + sx = -sx; + } + X += stdlib_strided_min_view_buffer_index( N, stride, offset ); // adjust array pointer + return API_SUFFIX(cblas_dasum)( N, X, sx ); } diff --git a/src/dasum_f.c b/src/dasum_f.c index a2f8f1c..dfd08c0 100644 --- a/src/dasum_f.c +++ b/src/dasum_f.c @@ -1,7 +1,7 @@ /** * @license Apache-2.0 * -* Copyright (c) 2018 The Stdlib Authors. +* Copyright (c) 2024 The Stdlib Authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -19,6 +19,7 @@ #include "stdlib/blas/base/dasum.h" #include "stdlib/blas/base/dasum_fortran.h" #include "stdlib/blas/base/shared.h" +#include "stdlib/strided/base/min_view_buffer_index.h" /** * Computes the sum of absolute values. @@ -26,10 +27,38 @@ * @param N number of indexed elements * @param X input array * @param stride stride length -* @return sum of absolute values +* @return sum */ double API_SUFFIX(c_dasum)( const CBLAS_INT N, const double *X, const CBLAS_INT stride ) { + CBLAS_INT sx; double sum; - dasumsub( &N, X, &stride, &sum ); + + sx = stride; + if ( sx < 0 ) { + sx = -sx; + } + dasumsub( &N, X, &sx, &sum ); + return sum; +} + +/** +* Computes the sum of absolute values using alternative indexing semantics. +* +* @param N number of indexed elements +* @param X input array +* @param stride stride length +* @param offset starting index +* @return sum +*/ +double API_SUFFIX(c_dasum_ndarray)( const CBLAS_INT N, const double *X, const CBLAS_INT stride, const CBLAS_INT offset ) { + CBLAS_INT sx; + double sum; + + sx = stride; + X += stdlib_strided_min_view_buffer_index( N, stride, offset ); // adjust array pointer + if ( sx < 0 ) { + sx = -sx; + } + dasumsub( &N, X, &sx, &sum ); return sum; } diff --git a/src/dasum_ndarray.c b/src/dasum_ndarray.c new file mode 100644 index 0000000..4b24276 --- /dev/null +++ b/src/dasum_ndarray.c @@ -0,0 +1,71 @@ +/** +* @license Apache-2.0 +* +* Copyright (c) 2024 The Stdlib Authors. +* +* Licensed under the Apache License, Version 2.0 (the "License"); +* you may not use this file except in compliance with the License. +* You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + +#include "stdlib/blas/base/dasum.h" +#include "stdlib/blas/base/shared.h" +#include "stdlib/math/base/special/abs.h" + +static const CBLAS_INT M = 6; + +/** +* Computes the sum of absolute values using alternative indexing semantics. +* +* @param N number of indexed elements +* @param X input array +* @param stride stride length +* @param offset starting index +* @return sum +*/ +double API_SUFFIX(c_dasum_ndarray)( const CBLAS_INT N, const double *X, const CBLAS_INT stride, const CBLAS_INT offset ) { + CBLAS_INT ix; + CBLAS_INT i; + CBLAS_INT m; + double sum; + + sum = 0.0; + if ( N <= 0 ) { + return sum; + } + ix = offset; + + // If the stride is equal to `1`, use unrolled loops... + if ( stride == 1 ) { + m = N % M; + + // If we have a remainder, run a clean-up loop... + if ( m > 0 ) { + for ( i = 0; i < m; i++ ) { + sum += stdlib_base_abs( X[ ix ] ); + ix += stride; + } + } + if ( N < M ) { + return sum; + } + for ( i = m; i < N; i += M ) { + sum += stdlib_base_abs( X[ ix ] ) + stdlib_base_abs( X[ ix+1 ] ) + stdlib_base_abs( X[ ix+2 ] ) + stdlib_base_abs( X[ ix+3 ] ) + stdlib_base_abs( X[ ix+4 ] ) + stdlib_base_abs( X[ ix+5 ] ); + ix += M; + } + return sum; + } + for ( i = 0; i < N; i ++ ) { + sum += stdlib_base_abs( X[ ix ] ); + ix += stride; + } + return sum; +} diff --git a/test/test.dasum.js b/test/test.dasum.js index 83dee05..17bd6cf 100644 --- a/test/test.dasum.js +++ b/test/test.dasum.js @@ -82,15 +82,23 @@ tape( 'if provided an `N` parameter less than or equal to `0`, the function retu t.end(); }); -tape( 'if provided a `stride` parameter less than or equal to `0`, the function returns `0`', function test( t ) { +tape( 'the function supports specifying a negative stride', function test( t ) { var x; var y; + var N; - x = new Float64Array( [ 1.0, -2.0, 3.0, -4.0, 5.0 ] ); + x = new Float64Array([ + 1.0, // 2 + -2.0, + 3.0, // 1 + -4.0, + 5.0 + ]); + N = 2; - y = dasum( x.length, x, -1 ); + y = dasum( N, x, -2 ); - t.strictEqual( y, 0.0, 'returns expected value' ); + t.strictEqual( y, 4.0, 'returns expected value' ); t.end(); }); diff --git a/test/test.dasum.native.js b/test/test.dasum.native.js index 9b1268d..4b09766 100644 --- a/test/test.dasum.native.js +++ b/test/test.dasum.native.js @@ -86,15 +86,23 @@ tape( 'if provided an `N` parameter less than or equal to `0`, the function retu t.end(); }); -tape( 'if provided a `stride` parameter less than or equal to `0`, the function returns `0`', opts, function test( t ) { +tape( 'the function supports specifying a negative stride', opts, function test( t ) { var x; var y; + var N; - x = new Float64Array( [ 1.0, -2.0, 3.0, -4.0, 5.0 ] ); + x = new Float64Array([ + 1.0, // 2 + -2.0, + 3.0, // 1 + -4.0, + 5.0 + ]); + N = 2; - y = dasum( x.length, x, -1 ); + y = dasum( N, x, -2 ); - t.strictEqual( y, 0.0, 'returns expected value' ); + t.strictEqual( y, 4.0, 'returns expected value' ); t.end(); }); diff --git a/test/test.ndarray.js b/test/test.ndarray.js index 4f28f3f..12b71ac 100644 --- a/test/test.ndarray.js +++ b/test/test.ndarray.js @@ -106,7 +106,7 @@ tape( 'if provided an `N` parameter less than or equal to `0`, the function retu t.end(); }); -tape( 'the function supports negative strides', function test( t ) { +tape( 'the function supports specifying a negative stride', function test( t ) { var x; var y; var N; diff --git a/test/test.ndarray.native.js b/test/test.ndarray.native.js index b6acbd8..3b33fa7 100644 --- a/test/test.ndarray.native.js +++ b/test/test.ndarray.native.js @@ -115,7 +115,7 @@ tape( 'if provided an `N` parameter less than or equal to `0`, the function retu t.end(); }); -tape( 'the function supports negative strides', opts, function test( t ) { +tape( 'the function supports specifying a negative stride', opts, function test( t ) { var x; var y; var N;