CA1833: Use AsSpan or AsMemory instead of Range-based indexers for getting Span or Memory portion of an array
Property | Value |
---|---|
Rule ID | CA1833 |
Title | Use AsSpan or AsMemory instead of Range-based indexers for getting Span or Memory portion of an array |
Category | Performance |
Fix is breaking or non-breaking | Non-breaking |
Enabled by default in .NET 8 | As suggestion |
Cause
When using a range-indexer on an array and implicitly assigning the value to Span<T> or Memory<T>.
Rule description
The range indexer on a Span<T> is a non-copying Slice operation. But for the range indexer on an array, the method GetSubArray will be used instead of Slice, which produces a copy of the requested portion of the array. This copy is usually unnecessary when it's implicitly used as a Span<T> or Memory<T> value. If a copy isn't intended, use the AsSpan or AsMemory method to avoid the unnecessary copy. If the copy is intended, either assign it to a local variable first or add an explicit cast. The analyzer only reports when an implicit cast is used on the result of the range indexer operation.
Detects
Implicit conversions:
Span<SomeT> slice = arr[a..b];
Memory<SomeT> slice = arr[a..b];
Does not detect
Explicit conversions:
Span<SomeT> slice = (Span<SomeT>)arr[a..b];
Memory<SomeT> slice = (Memory<SomeT>)arr[a..b];
How to fix violations
To fix a violation of this rule, use the AsSpan or AsMemory extension method to avoid creating unnecessary data copies.
class C
{
public void TestMethod(byte[] arr)
{
// The violation occurs for both statements below
Span<byte> tmp2 = arr[0..5];
Memory<byte> tmp4 = arr[5..10];
...
}
}
class C
{
public void TestMethod(byte[] arr)
{
// The violations fixed with AsSpan or AsMemory accordingly
Span<byte> tmp2 = arr.AsSpan()[0..5];
Memory<byte> tmp4 = arr.AsMemory()[5..10];
...
}
}
Tip
A code fix is available for this rule in Visual Studio. To use it, position the cursor on the violation and press Ctrl+. (period). Choose Use AsMemory instead of the Range-based indexer on an array from the list of options that's presented.
You can also avoid this warning by adding an explicit cast.
class C
{
public void TestMethod(byte[] arr)
{
// The violation occurs
Span<byte> tmp1 = arr[0..5];
Memory<byte> tmp2 = arr[5..10];
...
}
}
class C
{
public void TestMethod(byte[] arr)
{
// The violation fixed with explicit casting
Span<byte> tmp1 = (Span<byte>)arr[0..5];
Memory<byte> tmp2 = (Memory<byte>)arr[5..10];
...
}
}
When to suppress warnings
It's safe to suppress a violation of this rule if creating a copy is intended.
Suppress a warning
If you just want to suppress a single violation, add preprocessor directives to your source file to disable and then re-enable the rule.
#pragma warning disable CA1833
// The code that's violating the rule is on this line.
#pragma warning restore CA1833
To disable the rule for a file, folder, or project, set its severity to none
in the configuration file.
[*.{cs,vb}]
dotnet_diagnostic.CA1833.severity = none
For more information, see How to suppress code analysis warnings.
Related rules
- CA1831: Use AsSpan instead of Range-based indexers for string when appropriate
- CA1832: Use AsSpan or AsMemory instead of Range-based indexers for getting ReadOnlySpan or ReadOnlyMemory portion of an array
See also
Phản hồi
https://aka.ms/ContentUserFeedback.
Sắp ra mắt: Trong năm 2024, chúng tôi sẽ dần gỡ bỏ Sự cố với GitHub dưới dạng cơ chế phản hồi cho nội dung và thay thế bằng hệ thống phản hồi mới. Để biết thêm thông tin, hãy xem:Gửi và xem ý kiến phản hồi dành cho