33

C# has a high performance array copying function to copy arrays in place:

Array.Copy(source, destination, length)

It's faster than doing it manually ie.:

for (var i = 0; i < length; i++)
    destination[i] = source[i];

I am looking for an equivalent high performance copy function to copy arrays in place, for Int32Array and Float32Array in JavaScript and can find no such function:

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/TypedArray

The closest is copyWithin which only does a copy internally within an array.

Is there a built in high performance copy function for TypedArrays in place?

Plan B, is there a built in high performance clone function instead? (EDIT: looks like slice() is the answer to that)

6
  • u can use Array.join() Commented Feb 22, 2016 at 20:54
  • @علاء الدين, Array.join? that does not even return an array. Commented Feb 22, 2016 at 21:01
  • Possible duplicate of Copying array by value in JavaScript Commented Feb 22, 2016 at 21:02
  • 4
    @MikeMcCaughan I disagree that this question is a duplicate. This question asks first and foremost how to copy values into an existing array, while that question asks how to create a new array. (This question tolerates the creation of a new array only as a last resort.) In this case, the answer appears to be .set; in that case the answer is .slice. Nevertheless, I think that other question is a helpful pointer. Commented Feb 22, 2016 at 21:14
  • Can we get a sample data set to compare the answers in a performance test? Commented Feb 22, 2016 at 21:25

3 Answers 3

50

You're looking for .set which allows you to set the values of an array using an input array (or TypedArray), optionally starting at some offset on the destination array:

destination.set(source);
destination.set(source, offset);

Or, to set a limited amount of the input array:

destination.set(source.slice(limit), offset);

If you instead want to create a new TypedArray, you can simply use .slice:

source.slice();
Sign up to request clarification or add additional context in comments.

2 Comments

BTW If you're looking for efficiency you might use source.subarray(limit) instead of slice so only a new view is created and the same underlying data store is used (no intermediate data copy required).
It is really unfortunate that TypesArray.set() does not accept an optional third parameter to limit the number of entries to be copied. So currently creating an intermediate view using source.subarray(limit) seems to be the way to go.
8

You can clone an array using slice(0);.

var clone = myArray.slice(0);

And you can make it a native method:

Array.prototype.clone = function() {
    return this.slice(0);
};

Performance link comparing to loop

6 Comments

slice is the way to go. If that ain't high performance enough, then the downvoter should downvote JavaScript, not the messenger.
You don't need to 0. See the duplicate: stackoverflow.com/q/7486085/215552
@MikeMcCaughan, actually the 0 runs faster, and this was a performance question.
Thanks, actually for good reasons my preference is to copy into an existing array "in place" to minimize memory volatility and having to update references. Hence slice() is undesirable. The performance link seems to be for JS arrays, not TypedArrays.
Please do not extend the native array. It is much much slower than just doing .slice(0).
|
6

clone to an exist typedarray:

destination.set(source);
destination.set(source, offset);

clone to a new typedarray example: (It's fastest!)

var source = new Uint8Array([1,2,3]);
var cloned = new Uint8Array(source);

1 Comment

About using the constructor, good tip. Though I'd like to point out that if the cloned array already exists (ex you are using a double-buffer setup) then .set is (by my measurement) 20 times faster (1.5 ms self time vs 29.8 ms self time), as it does not need to allocate memory. (My test involved a pair of Uint32Arrays each with 10,000 items, containing semi-random data in a real-world use-case)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.