@stdlib/ndarray-vector-ctor 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/lib/main.js ADDED
@@ -0,0 +1,610 @@
1
+ /**
2
+ * @license Apache-2.0
3
+ *
4
+ * Copyright (c) 2025 The Stdlib Authors.
5
+ *
6
+ * Licensed under the Apache License, Version 2.0 (the "License");
7
+ * you may not use this file except in compliance with the License.
8
+ * You may obtain a copy of the License at
9
+ *
10
+ * http://www.apache.org/licenses/LICENSE-2.0
11
+ *
12
+ * Unless required by applicable law or agreed to in writing, software
13
+ * distributed under the License is distributed on an "AS IS" BASIS,
14
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ * See the License for the specific language governing permissions and
16
+ * limitations under the License.
17
+ */
18
+
19
+ /* eslint-disable max-len */
20
+
21
+ 'use strict';
22
+
23
+ // MODULES //
24
+
25
+ var isNonNegativeInteger = require( '@stdlib/assert-is-nonnegative-integer' ).isPrimitive;
26
+ var isIterableLike = require( '@stdlib/assert-is-iterable-like' );
27
+ var isCollection = require( '@stdlib/assert-is-collection' );
28
+ var isArrayBuffer = require( '@stdlib/assert-is-arraybuffer' );
29
+ var isPlainObject = require( '@stdlib/assert-is-plain-object' );
30
+ var isBuffer = require( '@stdlib/assert-is-buffer' );
31
+ var isDataType = require( '@stdlib/ndarray-base-assert-is-data-type' );
32
+ var hasOwnProp = require( '@stdlib/assert-has-own-property' );
33
+ var buffer = require( '@stdlib/ndarray-base-buffer' );
34
+ var typedarray = require( '@stdlib/array-typed' );
35
+ var copy = require( '@stdlib/array-base-copy' );
36
+ var ndarray = require( '@stdlib/ndarray-ctor' );
37
+ var defaults = require( '@stdlib/ndarray-defaults' );
38
+ var strides2offset = require( '@stdlib/ndarray-base-strides2offset' );
39
+ var arraybuffer2buffer = require( '@stdlib/buffer-from-arraybuffer' );
40
+ var array2buffer = require( '@stdlib/buffer-from-array' );
41
+ var copyBuffer = require( '@stdlib/buffer-from-buffer' );
42
+ var iterator2array = require( '@stdlib/array-from-iterator' );
43
+ var bytesPerElement = require( '@stdlib/ndarray-base-bytes-per-element' );
44
+ var ITERATOR_SYMBOL = require( '@stdlib/symbol-iterator' );
45
+ var format = require( '@stdlib/string-format' );
46
+
47
+
48
+ // VARIABLES //
49
+
50
+ var DEFAULT_DTYPE = defaults.get( 'dtypes.default' );
51
+ var DEFAULT_ORDER = defaults.get( 'order' );
52
+
53
+
54
+ // FUNCTIONS //
55
+
56
+ /**
57
+ * Tests whether a data type is a "generic" data type.
58
+ *
59
+ * @private
60
+ * @param {string} dtype - data type
61
+ * @returns {boolean} result
62
+ */
63
+ function isGenericDataType( dtype ) {
64
+ return ( dtype === 'generic' );
65
+ }
66
+
67
+ /**
68
+ * Tests whether a data type is a binary data type.
69
+ *
70
+ * @private
71
+ * @param {string} dtype - data type
72
+ * @returns {boolean} result
73
+ */
74
+ function isBinaryDataType( dtype ) {
75
+ return ( dtype === 'binary' );
76
+ }
77
+
78
+ /**
79
+ * Resolves the order of the output vector.
80
+ *
81
+ * @private
82
+ * @param {*} options - options argument
83
+ * @returns {string} order
84
+ */
85
+ function resolveOrder( options ) {
86
+ if ( hasOwnProp( options, 'order' ) ) {
87
+ return options.order;
88
+ }
89
+ return DEFAULT_ORDER;
90
+ }
91
+
92
+ /**
93
+ * Creates a one-dimensional ndarray from an ArrayBuffer.
94
+ *
95
+ * @private
96
+ * @param {string} dtype - data type
97
+ * @param {ArrayBuffer} buffer - ArrayBuffer
98
+ * @param {NonNegativeInteger} length - number of indexed elements
99
+ * @param {integer} stride - stride length (in units of elements)
100
+ * @param {NonNegativeInteger} byteOffset - byte offset of the first indexed element
101
+ * @param {string} order - memory layout (either row-major or column-major)
102
+ * @param {Options} [options] - function options
103
+ * @param {boolean} [options.readonly=false] - boolean indicating whether to return a read-only ndarray
104
+ * @param {string} [options.mode='throw'] - specifies how to handle indices which exceed ndarray dimensions
105
+ * @throws {TypeError} data type must be compatible with the provided ArrayBuffer
106
+ * @returns {ndarray} one-dimensional ndarray
107
+ *
108
+ * @example
109
+ * var numel = require( '@stdlib/ndarray-numel' );
110
+ * var ArrayBuffer = require( '@stdlib/array-buffer' );
111
+ *
112
+ * var buf = new ArrayBuffer( 32 );
113
+ * var v = arraybuffer2vector( 'float64', buf, 4, 1, 0, 'row-major' );
114
+ * // returns <ndarray>
115
+ *
116
+ * var len = numel( v );
117
+ * // returns 4
118
+ *
119
+ * @example
120
+ * var numel = require( '@stdlib/ndarray-numel' );
121
+ * var ArrayBuffer = require( '@stdlib/array-buffer' );
122
+ *
123
+ * var buf = new ArrayBuffer( 32 );
124
+ * var v = arraybuffer2vector( 'float32', buf, 8, 1, 0, 'row-major' );
125
+ * // returns <ndarray>
126
+ *
127
+ * var len = numel( v );
128
+ * // returns 8
129
+ *
130
+ * @example
131
+ * var numel = require( '@stdlib/ndarray-numel' );
132
+ * var ArrayBuffer = require( '@stdlib/array-buffer' );
133
+ *
134
+ * var buf = new ArrayBuffer( 32 );
135
+ * var v = arraybuffer2vector( 'float64', buf, 4, -1, 32, 'row-major' );
136
+ * // returns <ndarray>
137
+ *
138
+ * var len = numel( v );
139
+ * // returns 4
140
+ *
141
+ * @example
142
+ * var numel = require( '@stdlib/ndarray-numel' );
143
+ * var ArrayBuffer = require( '@stdlib/array-buffer' );
144
+ *
145
+ * var buf = new ArrayBuffer( 32 );
146
+ * var v = arraybuffer2vector( 'float64', buf, 2, -1, 24, 'row-major' );
147
+ * // returns <ndarray>
148
+ *
149
+ * var len = numel( v );
150
+ * // returns 2
151
+ */
152
+ function arraybuffer2vector( dtype, buffer, length, stride, byteOffset, order, options ) { // TODO: consider moving to `@stdlib/ndarray/from-arraybuffer` and generalize to n-dimensions such that `length` becomes `shape` and `stride` becomes `strides`
153
+ var buf;
154
+ var sh;
155
+ var st;
156
+ var N;
157
+ var o;
158
+
159
+ if ( isGenericDataType( dtype ) ) {
160
+ throw new TypeError( format( 'invalid argument. ArrayBuffer is incompatible with the specified data type. Value: `%s`.', dtype ) );
161
+ }
162
+ o = byteOffset;
163
+
164
+ // Compute the number of underlying elements across which the vector view will span:
165
+ N = length * stride;
166
+
167
+ // Adjust the byte offset to point to the element marking the beginning of the view:
168
+ if ( stride < 0 ) { // TODO: the following is effectively unreachable code, as provided strides are never anything other than unity; however, we keep this around in the event that we want to extract this function to a separate package and would like to maintain generality
169
+ N *= -1;
170
+ o -= N * bytesPerElement( dtype );
171
+ }
172
+ // Create the underlying ndarray buffer:
173
+ if ( isBinaryDataType( dtype ) ) {
174
+ buf = arraybuffer2buffer( buffer, o, N );
175
+ } else {
176
+ buf = typedarray( buffer, o, N, dtype );
177
+ }
178
+ // Resolve ndarray meta data:
179
+ sh = [ length ];
180
+ st = [ stride ];
181
+ o = strides2offset( sh, st );
182
+
183
+ // Return a new ndarray instance:
184
+ if ( arguments.length > 6 ) {
185
+ return new ndarray( dtype, buf, sh, st, o, order, options );
186
+ }
187
+ return new ndarray( dtype, buf, sh, st, o, order );
188
+ }
189
+
190
+ /**
191
+ * Returns a vector having a specified data type.
192
+ *
193
+ * @private
194
+ * @param {(NonNegativeInteger|Collection|ArrayBuffer|Buffer|Iterable|Options)} arg - length, typed array, array-like object, buffer, iterable, or options object
195
+ * @param {string} dtype - data type
196
+ * @param {(Options|null)} options - function options
197
+ * @param {boolean} [options.readonly=false] - boolean indicating whether to return a read-only ndarray
198
+ * @param {string} [options.mode='throw'] - specifies how to handle indices which exceed ndarray dimensions
199
+ * @returns {(ndarray|null)} one-dimensional ndarray
200
+ *
201
+ * @example
202
+ * var getDType = require( '@stdlib/ndarray-dtype' );
203
+ * var numel = require( '@stdlib/ndarray-numel' );
204
+ *
205
+ * var v = vectorWithDType( 10, 'float64', {} );
206
+ * // returns <ndarray>
207
+ *
208
+ * var len = numel( v );
209
+ * // returns 10
210
+ *
211
+ * var dt = getDType( v );
212
+ * // returns 'float64'
213
+ *
214
+ * @example
215
+ * var getDType = require( '@stdlib/ndarray-dtype' );
216
+ * var numel = require( '@stdlib/ndarray-numel' );
217
+ *
218
+ * var v = vectorWithDType( [ 1, 2, 3, 4 ], 'generic', {} );
219
+ * // returns <ndarray>
220
+ *
221
+ * var len = numel( v );
222
+ * // returns 4
223
+ *
224
+ * var dt = getDType( v );
225
+ * // returns 'generic'
226
+ *
227
+ * @example
228
+ * var getDType = require( '@stdlib/ndarray-dtype' );
229
+ * var numel = require( '@stdlib/ndarray-numel' );
230
+ * var ArrayBuffer = require( '@stdlib/array-buffer' );
231
+ *
232
+ * var buf = new ArrayBuffer( 32 );
233
+ * var v = vectorWithDType( buf, 'float64', {} );
234
+ * // returns <ndarray>
235
+ *
236
+ * var len = numel( v );
237
+ * // returns 4
238
+ *
239
+ * var dt = getDType( v );
240
+ * // returns 'float64'
241
+ *
242
+ * @example
243
+ * var getDType = require( '@stdlib/ndarray-dtype' );
244
+ * var numel = require( '@stdlib/ndarray-numel' );
245
+ *
246
+ * var v = vectorWithDType( {}, 'float64', null );
247
+ * // returns <ndarray>
248
+ *
249
+ * var len = numel( v );
250
+ * // returns 0
251
+ *
252
+ * var dt = getDType( v );
253
+ * // returns 'float64'
254
+ *
255
+ * @example
256
+ * var getDType = require( '@stdlib/ndarray-dtype' );
257
+ * var numel = require( '@stdlib/ndarray-numel' );
258
+ * var array2iterator = require( '@stdlib/array-to-iterator' );
259
+ *
260
+ * var v = vectorWithDType( array2iterator( [ 1, 2, 3, 4 ] ), 'generic', {} );
261
+ * // returns <ndarray>
262
+ *
263
+ * var len = numel( v );
264
+ * // returns 4
265
+ *
266
+ * var dt = getDType( v );
267
+ * // returns 'generic'
268
+ */
269
+ function vectorWithDType( arg, dtype, options ) {
270
+ var opts;
271
+ var buf;
272
+
273
+ // Note: in all of the following, we delegate option validation to the ndarray constructor...
274
+ if ( options === null ) {
275
+ opts = {};
276
+ } else {
277
+ opts = options;
278
+ }
279
+ // Case: vector( length )
280
+ if ( isNonNegativeInteger( arg ) ) {
281
+ buf = buffer( dtype, arg );
282
+ return new ndarray( dtype, buf, [ buf.length ], [ 1 ], 0, resolveOrder( opts ), opts );
283
+ }
284
+ // Case: vector( Buffer )
285
+ if ( isBuffer( arg ) ) {
286
+ if ( isGenericDataType( dtype ) ) {
287
+ buf = copy( arg );
288
+ } else if ( isBinaryDataType( dtype ) ) {
289
+ buf = copyBuffer( arg );
290
+ } else {
291
+ buf = typedarray( arg, dtype );
292
+ }
293
+ return new ndarray( dtype, buf, [ buf.length ], [ 1 ], 0, resolveOrder( opts ), opts );
294
+ }
295
+ // Case: vector( collection )
296
+ if ( isCollection( arg ) ) {
297
+ if ( isGenericDataType( dtype ) ) {
298
+ buf = copy( arg );
299
+ } else if ( isBinaryDataType( dtype ) ) {
300
+ buf = array2buffer( arg ); // note: we assume that `arg` is an array of octets
301
+ } else {
302
+ buf = typedarray( arg, dtype );
303
+ }
304
+ return new ndarray( dtype, buf, [ buf.length ], [ 1 ], 0, resolveOrder( opts ), opts );
305
+ }
306
+ // Case: vector( ArrayBuffer )
307
+ if ( isArrayBuffer( arg ) ) {
308
+ return arraybuffer2vector( dtype, arg, arg.byteLength/bytesPerElement( dtype ), 1, 0, resolveOrder( opts ), opts );
309
+ }
310
+ // Case: vector( Iterable )
311
+ if ( isIterableLike( arg ) ) {
312
+ buf = arg[ ITERATOR_SYMBOL ]();
313
+ buf = iterator2array( buf );
314
+ if ( isBinaryDataType( dtype ) ) {
315
+ buf = array2buffer( buf );
316
+ } else if ( !isGenericDataType( dtype ) ) {
317
+ buf = typedarray( buf, dtype );
318
+ }
319
+ return new ndarray( dtype, buf, [ buf.length ], [ 1 ], 0, resolveOrder( opts ), opts );
320
+ }
321
+ // Case: vector( options )
322
+ if ( options === null && isPlainObject( arg ) ) {
323
+ buf = buffer( dtype, 0 );
324
+ return new ndarray( dtype, buf, [ buf.length ], [ 1 ], 0, resolveOrder( arg ), arg );
325
+ }
326
+ return null;
327
+ }
328
+
329
+
330
+ // MAIN //
331
+
332
+ /**
333
+ * Creates a vector (i.e., a one-dimensional ndarray).
334
+ *
335
+ * ## Notes
336
+ *
337
+ * - This API is intended to match the conventions of `@stdlib/array/typed`, which has a similar signature.
338
+ *
339
+ * @param {(NonNegativeInteger|Collection|ArrayBuffer|Iterable)} [arg] - length, typed array, array-like object, buffer, or iterable
340
+ * @param {NonNegativeInteger} [byteOffset=0] - byte offset
341
+ * @param {NonNegativeInteger} [length] - view length
342
+ * @param {string} [dtype='float64'] - data type
343
+ * @param {Options} [options] - function options
344
+ * @param {boolean} [options.readonly=false] - boolean indicating whether to return a read-only vector
345
+ * @param {string} [options.mode='throw'] - specifies how to handle indices which exceed vector dimensions
346
+ * @param {string} [options.order='row-major'] - memory layout (either row-major or column-major)
347
+ * @throws {TypeError} first argument must be either a length, typed array, array-like object, buffer, iterable, data type, or options object
348
+ * @throws {TypeError} must provide valid options
349
+ * @returns {ndarray} one-dimensional ndarray
350
+ *
351
+ * @example
352
+ * var getDType = require( '@stdlib/ndarray-dtype' );
353
+ * var numel = require( '@stdlib/ndarray-numel' );
354
+ *
355
+ * var arr = vector();
356
+ * // returns <ndarray>
357
+ *
358
+ * var len = numel( arr );
359
+ * // returns 0
360
+ *
361
+ * var dt = getDType( arr );
362
+ * // returns 'float64'
363
+ *
364
+ * @example
365
+ * var getDType = require( '@stdlib/ndarray-dtype' );
366
+ * var numel = require( '@stdlib/ndarray-numel' );
367
+ *
368
+ * var arr = vector( 2 );
369
+ * // returns <ndarray>
370
+ *
371
+ * var len = numel( arr );
372
+ * // returns 2
373
+ *
374
+ * var dt = getDType( arr );
375
+ * // returns 'float64'
376
+ *
377
+ * @example
378
+ * var getDType = require( '@stdlib/ndarray-dtype' );
379
+ * var numel = require( '@stdlib/ndarray-numel' );
380
+ *
381
+ * var arr = vector( [ 1.0, 2.0 ] );
382
+ * // returns <ndarray>
383
+ *
384
+ * var len = numel( arr );
385
+ * // returns 2
386
+ *
387
+ * var dt = getDType( arr );
388
+ * // returns 'float64'
389
+ *
390
+ * @example
391
+ * var getDType = require( '@stdlib/ndarray-dtype' );
392
+ * var numel = require( '@stdlib/ndarray-numel' );
393
+ *
394
+ * var arr = vector( [ 1.0, 2.0 ], 'float32' );
395
+ * // returns <ndarray>
396
+ *
397
+ * var len = numel( arr );
398
+ * // returns 2
399
+ *
400
+ * var dt = getDType( arr );
401
+ * // returns 'float32'
402
+ *
403
+ * @example
404
+ * var getDType = require( '@stdlib/ndarray-dtype' );
405
+ * var numel = require( '@stdlib/ndarray-numel' );
406
+ * var ArrayBuffer = require( '@stdlib/array-buffer' );
407
+ *
408
+ * var buf = new ArrayBuffer( 32 );
409
+ * var arr = vector( buf );
410
+ * // returns <ndarray>
411
+ *
412
+ * var len = numel( arr );
413
+ * // returns 4
414
+ *
415
+ * var dt = getDType( arr );
416
+ * // returns 'float64'
417
+ *
418
+ * @example
419
+ * var getDType = require( '@stdlib/ndarray-dtype' );
420
+ * var numel = require( '@stdlib/ndarray-numel' );
421
+ * var ArrayBuffer = require( '@stdlib/array-buffer' );
422
+ *
423
+ * var buf = new ArrayBuffer( 32 );
424
+ * var arr = vector( buf, 16 );
425
+ * // returns <ndarray>
426
+ *
427
+ * var len = numel( arr );
428
+ * // returns 2
429
+ *
430
+ * var dt = getDType( arr );
431
+ * // returns 'float64'
432
+ *
433
+ * @example
434
+ * var getDType = require( '@stdlib/ndarray-dtype' );
435
+ * var numel = require( '@stdlib/ndarray-numel' );
436
+ * var ArrayBuffer = require( '@stdlib/array-buffer' );
437
+ *
438
+ * var buf = new ArrayBuffer( 64 );
439
+ * var arr = vector( buf, 16, 2 );
440
+ * // returns <ndarray>
441
+ *
442
+ * var len = numel( arr );
443
+ * // returns 2
444
+ *
445
+ * var dt = getDType( arr );
446
+ * // returns 'float64'
447
+ */
448
+ function vector() {
449
+ var nargs;
450
+ var arg0;
451
+ var arg1;
452
+ var arg2;
453
+ var arg3;
454
+ var arg4;
455
+ var buf;
456
+ var out;
457
+
458
+ nargs = arguments.length;
459
+
460
+ // Case: vector()
461
+ if ( nargs === 0 ) {
462
+ buf = buffer( DEFAULT_DTYPE, 0 );
463
+ return new ndarray( DEFAULT_DTYPE, buf, [ buf.length ], [ 1 ], 0, DEFAULT_ORDER );
464
+ }
465
+ arg0 = arguments[ 0 ];
466
+
467
+ // Case: vector( arg0 );
468
+ if ( nargs === 1 ) {
469
+ if ( isDataType( arg0 ) ) {
470
+ return vectorWithDType( 0, arg0, null );
471
+ }
472
+ out = vectorWithDType( arg0, DEFAULT_DTYPE, null );
473
+ if ( out === null ) {
474
+ throw new TypeError( format( 'invalid argument. Must provide a length, ArrayBuffer, typed array, array-like object, iterable, data type, or options object. Value: `%s`.', arg0 ) );
475
+ }
476
+ return out;
477
+ }
478
+ arg1 = arguments[ 1 ];
479
+
480
+ // Case: vector( arg0, arg1 )
481
+ if ( nargs === 2 ) {
482
+ // Case: vector( dtype, options )
483
+ if ( isDataType( arg0 ) ) {
484
+ if ( arg1 === null ) {
485
+ throw new TypeError( format( 'invalid argument. Options argument must be an object. Value: `%s`.', arg1 ) );
486
+ }
487
+ return vectorWithDType( 0, arg0, arg1 );
488
+ }
489
+ // Case: vector( arg0, dtype )
490
+ if ( isDataType( arg1 ) ) {
491
+ out = vectorWithDType( arg0, arg1, null );
492
+ if ( out === null ) {
493
+ throw new TypeError( format( 'invalid argument. First argument must be a length, ArrayBuffer, typed array, array-like object, or iterable. Value: `%s`.', arg0 ) );
494
+ }
495
+ return out;
496
+ }
497
+ // Case: vector( ArrayBuffer, byteOffset )
498
+ if ( isNonNegativeInteger( arg1 ) ) {
499
+ if ( !isArrayBuffer( arg0 ) ) {
500
+ throw new TypeError( format( 'invalid argument. First argument must be an ArrayBuffer. Value: `%s`.', arg0 ) );
501
+ }
502
+ return arraybuffer2vector( DEFAULT_DTYPE, arg0, (arg0.byteLength-arg1)/bytesPerElement( DEFAULT_DTYPE ), 1, arg1, DEFAULT_ORDER );
503
+ }
504
+ // Case: vector( arg0, options )
505
+ if ( arg1 === null ) {
506
+ throw new TypeError( format( 'invalid argument. Options argument must be an object. Value: `%s`.', arg1 ) );
507
+ }
508
+ out = vectorWithDType( arg0, DEFAULT_DTYPE, arg1 );
509
+ if ( out === null ) {
510
+ throw new TypeError( format( 'invalid argument. First argument must be a length, ArrayBuffer, typed array, array-like object, or iterable. Value: `%s`.', arg0 ) );
511
+ }
512
+ return out;
513
+ }
514
+ arg2 = arguments[ 2 ];
515
+
516
+ // Case: vector( arg0, arg1, arg2 )
517
+ if ( nargs === 3 ) {
518
+ // Case: vector( ArrayBuffer, byteOffset, dtype )
519
+ if ( isDataType( arg2 ) ) {
520
+ if ( !isArrayBuffer( arg0 ) ) {
521
+ throw new TypeError( format( 'invalid argument. First argument must be an ArrayBuffer. Value: `%s`.', arg0 ) );
522
+ }
523
+ if ( !isNonNegativeInteger( arg1 ) ) {
524
+ throw new TypeError( format( 'invalid argument. Byte offset must be a nonnegative integer. Value: `%s`.', arg1 ) );
525
+ }
526
+ return arraybuffer2vector( arg2, arg0, (arg0.byteLength-arg1)/bytesPerElement( arg2 ), 1, arg1, DEFAULT_ORDER );
527
+ }
528
+ // Case: vector( arg0, dtype, options )
529
+ if ( isDataType( arg1 ) ) {
530
+ if ( arg2 === null ) {
531
+ throw new TypeError( format( 'invalid argument. Options argument must be an object. Value: `%s`.', arg2 ) );
532
+ }
533
+ out = vectorWithDType( arg0, arg1, arg2 );
534
+ if ( out === null ) {
535
+ throw new TypeError( format( 'invalid argument. First argument must be a length, ArrayBuffer, typed array, array-like object, or iterable. Value: `%s`.', arg0 ) );
536
+ }
537
+ return out;
538
+ }
539
+ // Case: vector( ArrayBuffer, byteOffset, arg2 )
540
+ if ( !isArrayBuffer( arg0 ) ) {
541
+ throw new TypeError( format( 'invalid argument. First argument must be an ArrayBuffer. Value: `%s`.', arg0 ) );
542
+ }
543
+ if ( !isNonNegativeInteger( arg1 ) ) {
544
+ throw new TypeError( format( 'invalid argument. Byte offset must be a nonnegative integer. Value: `%s`.', arg1 ) );
545
+ }
546
+ // Case: vector( ArrayBuffer, byteOffset, length )
547
+ if ( isNonNegativeInteger( arg2 ) ) {
548
+ return arraybuffer2vector( DEFAULT_DTYPE, arg0, arg2, 1, arg1, DEFAULT_ORDER );
549
+ }
550
+ // Case: vector( ArrayBuffer, byteOffset, options )
551
+ if ( arg2 === null ) {
552
+ throw new TypeError( format( 'invalid argument. Options argument must be an object. Value: `%s`.', arg2 ) );
553
+ }
554
+ return arraybuffer2vector( DEFAULT_DTYPE, arg0, (arg0.byteLength-arg1)/bytesPerElement( DEFAULT_DTYPE ), 1, arg1, resolveOrder( arg2 ), arg2 );
555
+ }
556
+ arg3 = arguments[ 3 ];
557
+
558
+ // Case: vector( ArrayBuffer, byteOffset, arg2, arg3 )
559
+ if ( nargs === 4 ) {
560
+ if ( !isArrayBuffer( arg0 ) ) {
561
+ throw new TypeError( format( 'invalid argument. First argument must be an ArrayBuffer. Value: `%s`.', arg0 ) );
562
+ }
563
+ if ( !isNonNegativeInteger( arg1 ) ) {
564
+ throw new TypeError( format( 'invalid argument. Byte offset must be a nonnegative integer. Value: `%s`.', arg1 ) );
565
+ }
566
+ // Case: vector( ArrayBuffer, byteOffset, length, dtype )
567
+ if ( isNonNegativeInteger( arg2 ) ) {
568
+ if ( isDataType( arg3 ) ) {
569
+ return arraybuffer2vector( arg3, arg0, arg2, 1, arg1, DEFAULT_ORDER );
570
+ }
571
+ // Case: vector( ArrayBuffer, byteOffset, length, options )
572
+ if ( !isPlainObject( arg3 ) ) {
573
+ throw new TypeError( format( 'invalid argument. Options argument must be an object. Value: `%s`.', arg3 ) );
574
+ }
575
+ return arraybuffer2vector( DEFAULT_DTYPE, arg0, arg2, 1, arg1, resolveOrder( arg3 ), arg3 );
576
+ }
577
+ // Case: vector( ArrayBuffer, byteOffset, dtype, options )
578
+ if ( !isDataType( arg2 ) ) {
579
+ throw new TypeError( format( 'invalid argument. Third argument must be a recognized/supported data type. Value: `%s`.', arg2 ) );
580
+ }
581
+ if ( !isPlainObject( arg3 ) ) {
582
+ throw new TypeError( format( 'invalid argument. Options argument must be an object. Value: `%s`.', arg3 ) );
583
+ }
584
+ return arraybuffer2vector( arg2, arg0, (arg0.byteLength-arg1)/bytesPerElement( arg2 ), 1, arg1, resolveOrder( arg3 ), arg3 );
585
+ }
586
+ arg4 = arguments[ 4 ];
587
+
588
+ // Case: vector( ArrayBuffer, byteOffset, length, dtype, options )
589
+ if ( !isArrayBuffer( arg0 ) ) {
590
+ throw new TypeError( format( 'invalid argument. First argument must be an ArrayBuffer. Value: `%s`.', arg0 ) );
591
+ }
592
+ if ( !isNonNegativeInteger( arg1 ) ) {
593
+ throw new TypeError( format( 'invalid argument. Byte offset must be a nonnegative integer. Value: `%s`.', arg1 ) );
594
+ }
595
+ if ( !isNonNegativeInteger( arg2 ) ) {
596
+ throw new TypeError( format( 'invalid argument. Length must be a nonnegative integer. Value: `%s`.', arg2 ) );
597
+ }
598
+ if ( !isDataType( arg3 ) ) {
599
+ throw new TypeError( format( 'invalid argument. Fourth argument must be a recognized/supported data type. Value: `%s`.', arg3 ) );
600
+ }
601
+ if ( !isPlainObject( arg4 ) ) {
602
+ throw new TypeError( format( 'invalid argument. Options argument must be an object. Value: `%s`.', arg4 ) );
603
+ }
604
+ return arraybuffer2vector( arg3, arg0, arg2, 1, arg1, resolveOrder( arg4 ), arg4 );
605
+ }
606
+
607
+
608
+ // EXPORTS //
609
+
610
+ module.exports = vector;
@@ -0,0 +1,82 @@
1
+ /**
2
+ * @license Apache-2.0
3
+ *
4
+ * Copyright (c) 2025 The Stdlib Authors.
5
+ *
6
+ * Licensed under the Apache License, Version 2.0 (the "License");
7
+ * you may not use this file except in compliance with the License.
8
+ * You may obtain a copy of the License at
9
+ *
10
+ * http://www.apache.org/licenses/LICENSE-2.0
11
+ *
12
+ * Unless required by applicable law or agreed to in writing, software
13
+ * distributed under the License is distributed on an "AS IS" BASIS,
14
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ * See the License for the specific language governing permissions and
16
+ * limitations under the License.
17
+ */
18
+
19
+ 'use strict';
20
+
21
+ // MODULES //
22
+
23
+ var isObject = require( '@stdlib/assert-is-plain-object' );
24
+ var hasOwnProp = require( '@stdlib/assert-has-own-property' );
25
+ var isBoolean = require( '@stdlib/assert-is-boolean' ).isPrimitive;
26
+ var isIndexMode = require( '@stdlib/ndarray-base-assert-is-index-mode' );
27
+ var isOrder = require( '@stdlib/ndarray-base-assert-is-order' );
28
+ var format = require( '@stdlib/string-format' );
29
+
30
+
31
+ // MAIN //
32
+
33
+ /**
34
+ * Validates function options.
35
+ *
36
+ * @private
37
+ * @param {Object} opts - destination object
38
+ * @param {Options} options - function options
39
+ * @param {boolean} [options.readonly] - boolean indicating whether to return a read-only vector
40
+ * @param {string} [options.mode] - specifies how to handle indices which exceed vector dimensions
41
+ * @param {string} [options.order] - memory layout (either row-major or column-major)
42
+ * @returns {(Error|null)} null or an error object
43
+ *
44
+ * @example
45
+ * var opts = {};
46
+ * var options = {
47
+ * 'readonly': true
48
+ * };
49
+ * var err = validate( opts, options );
50
+ * if ( err ) {
51
+ * throw err;
52
+ * }
53
+ */
54
+ function validate( opts, options ) {
55
+ if ( !isObject( options ) ) {
56
+ return new TypeError( format( 'invalid argument. Options argument must be an object. Value: `%s`.', options ) );
57
+ }
58
+ if ( hasOwnProp( options, 'readonly' ) ) {
59
+ opts.readonly = options.readonly;
60
+ if ( !isBoolean( opts.readonly ) ) {
61
+ return new TypeError( format( 'invalid option. `%s` option must be a boolean. Option: `%s`.', 'readonly', opts.readonly ) );
62
+ }
63
+ }
64
+ if ( hasOwnProp( options, 'mode' ) ) {
65
+ opts.mode = options.mode;
66
+ if ( !isIndexMode( opts.mode ) ) {
67
+ return new TypeError( format( 'invalid option. `%s` option must be a valid index mode. Option: `%s`.', 'mode', opts.mode ) );
68
+ }
69
+ }
70
+ if ( hasOwnProp( options, 'order' ) ) {
71
+ opts.order = options.order;
72
+ if ( !isOrder( opts.order ) ) {
73
+ return new TypeError( format( 'invalid option. `%s` option must be a memory layout. Option: `%s`.', 'order', opts.order ) );
74
+ }
75
+ }
76
+ return null;
77
+ }
78
+
79
+
80
+ // EXPORTS //
81
+
82
+ module.exports = validate;