我有一个(ReadOnly)Span<byte>
,我想从中解码一个字符串。
仅在.NET Core 2.1中,我具有新的重载功能,可以从其中解码字符串而无需复制字节:
Encoding.GetString(ReadOnlySpan<byte> bytes);
在.NET Standard 2.0和.NET 4.6(我也要支持)中,我只有经典的重载:
Encoding.GetString(byte[] bytes);
Encoding.GetString(byte* bytes, int byteCount);
第一个需要将字节的副本复制到我要避免的数组中。
第二个需要一个字节指针,所以我考虑从我的跨度中获取一个,例如
Encoding.GetString(Unsafe.GetPointer<byte>(span.Slice(100)))
...但是我未能为此找到实际的方法。我尝试了void* Unsafe.AsPointer<T>(ref T value)
,但无法将范围传递给它,也找不到其他处理指针(和范围)的方法。
这完全有可能吗?如果可以,怎么办?
答案 0 :(得分:6)
如果您使用的是C#7.3或更高版本,则可以使用对fixed
语句进行的扩展,该扩展可以对类型(其中GetPinnableReference
和{{1 }}有):
Span
在处理指针时,当然需要一个ReadOnlySpan
上下文。
C#7.0到7.2没有此功能,但允许以下操作:
fixed (byte* bp = bytes) {
...
}
答案 1 :(得分:3)
尝试一下:
Span<byte> bytes = ...;
string s = Encoding.UTF8.GetString((byte*)Unsafe.AsPointer(ref bytes.GetPinnableReference()),
bytes.Length);