Reputation: 63728
Given byte[] buffer
I'd like to create a new array from a sub-array. A method signature might look like byte[] SubArray(byte[] buffer, int start, int length)
but I'd probably rather just have a neat 1-liner than a method.
Here's a nice neat LINQ version but it feels like this mightn't be very efficient. Is there a standard library method that does this or would I have to create a new array then copy to it?
var subArray = buffer.Skip(start).Take(length).ToArray();
Upvotes: 2
Views: 429
Reputation:
subArray = buffer.Skip(2).Take(3).ToArray();
subArray = buffer.ToList().GetRange(2, 3).ToArray();
subArray = Enumerable.Range(2, 3).Select(x => buffer[x]).ToArray();
subArray = buffer[2..5];
This is a new feature in c# 8. I couldn't find any specific name but you'll find it by googling something like "c# range feature" or "c# range operator" or "c# binary infix operator with two expressions" or "Range Syntax c#". See Docs.
subArray = new byte[3];
Array.ConstrainedCopy(buffer, 2, subArray, 0, 3);
subArray = new byte[3];
Array.Copy(buffer, 2, subArray, 0, 3);
Upvotes: 2
Reputation: 1062885
There is no efficient way that involves creating a new array, however, there are other ways you can look at a portion of an array:
Memory<byte>
/ ReadOnlyMemory<byte>
- effectively this is a "span provider"Span<byte>
/ ReadOnlySpan<byte>
- abstract view over any kind of raw memory (including arrays, interior pointers, and unmanaged memory), but can only be held on the stack - if you need to store it, you need the "memory", not the "span")ArraySegment<byte>
- explicitly just describes a vector/offset/countAll of the above have constructors that take a byte[]
and an offset/count pair.
None of these require allocating / copying.
If you really really want a byte[]
, then:
var newArray = new byte[length];
Buffer.BlockCopy(oldArray, start, newArray, 0, length);
Upvotes: 3