Reputation: 23
The documentation for both Vector and Vector128 structs are really similar and there is an AsVector/AsVector128 method to switch between them. However, is there a case where I should use one over the other one?
I looked at the implementation of these two structures and I noticed optimization attributes for JIT in addition for vectors128. Does this mean that only Vector128 is optimized (for specific architecture)? Is it supported under all platforms? So is there a case where the use of Vector128 would cause a NotSupportedException? Or I'm completely wrong and Vectors is just an old structure from the pre net Core 3.0 ?
Upvotes: 0
Views: 56
Reputation: 36629
The System.Numerics.Vector<T>
is intended to use whatever vector length is available on the platform, including if no SIMD available at all.
System.Runtime.Intrinsics.Vector128<T>
on the other hand has a fixed number of bits, and that may allow you optimize your code better than the compiler can. It also includes platform specific methods to enable further optimizations. This may not work if the platform does not support a specific vector width. In theory the compiler could reduce the vector width, or issue scalar code if the specific width is not available, but I'm not sure if it does so. 128 bits tend to be the "standard" SIMD width, so should be a fairly safe option.
Hardware Intrinsics in .NET Core compares the performance of Vector<T>
with the intrinsic variants. It suggest summing numbers using intrinsics is about 3 times faster, but the article is quite old, so your results may vary.
In conclusion, there are use cases for each option, but if you really want to know what option is fastest for your particular use case you might need to write your own benchmark comparing them.
Upvotes: 0
Reputation: 143098
Vector128
would cause a NotSupportedException
?Yes, but not in the way you expect. It will result in NotSupportedException
when used with unsupported type (see Vector128.Create
):
The type of value (T) is not supported.
I.e. when IsSupported
returns false
- see the implementation.
The type itself is intended for cross-platform usage but will provide performance gains if corresponding hardware instructions are available - see Vector128.IsHardwareAccelerated
.
Both structures were introduced to support vectorization and corresponding low-level optimization of parallel algorithms. Vector128
allows more fine-grained control. From API Proposal: Add Intel hardware intrinsic functions and namespace:
Currently, .NET provides
System.Numerics.Vector<T>
and related intrinsic functions as a cross-platform SIMD interface that automatically matches proper hardware support at JIT-compile time (e.g.Vector<T>
is size of 128-bit on SSE2 machines or 256-bit on AVX2 machines). However, there is no way to simultaneously use different sizeVector<T>
, which limits the flexibility of SIMD intrinsics. For example, on AVX2 machines, XMM registers are not accessible fromVector<T>
, but certain instructions have to work on XMM registers (i.e. SSE4.2). Consequently, this proposal introducesVector128<T>
andVector256<T>
in a new namespaceSystem.Runtime.Intrinsics
See also:
Upvotes: 0