Use Span<T> as C# class level variable.

huangapple go评论62阅读模式
英文:

Use Span<T> as C# class level variable

问题

我正在为逗号分隔的流(网络)编写一个高性能解析器。 我的目标是直接从二进制转换为dotnet原语。 到目前为止,根据我的测试,Span<T>的性能非常出色,但由于ref结构固有的限制,这种类型很难使用。 在尝试寻找在整个应用程序中高效存储Span<T>常量(逗号、换行等)的方法时,我遇到了难题。 唯一看起来存在的解决方案是将它们存储为byte,并在方法的类主体中进行转换...或在每个方法主体中硬编码Span&lt;byte&gt; delimiter = Encoding.UTF8.GetBytes(&quot;\r\n&quot;)

以下是我想要实现的内容,但它会出现错误 - `CS8345 Field or auto-implemented property cannot be of type 'Span<byte>' unless it is an instance member of a ref struct.

public class Parser
{
    Span&lt;byte&gt; NewLine = new byte[]{ (byte)&#39;\n&#39; };
}
英文:

I'm writing a high-performance parser for a comma delimited stream (network). My goal is to parse and convert directly from binary to dotnet primitives. Based on my testing thus far, Span<T> performance is incredible, but the type is difficult to work with due to restrictions inherent to ref structs. I've hit a roadblock trying to find an efficient way to store Span<T> constants (comma, newline, etc.) used throughout my application. The only solution that seems to exist to store them as byte and convert them in the class bodies of methods...or hardcode Span&lt;byte&gt; delimiter = Encoding.UTF8.GetBytes(&quot;\r\n&quot;) in every method body.

The following is what I'd like to achieve but it gives the error - `CS8345 Field or auto-implemented property cannot be of type 'Span<byte>' unless it is an instance member of a ref struct.

public class Parser
{
    Span&lt;byte&gt; NewLine = new byte[]{ (byte)&#39;\n&#39; };
}

There's got to be a better way! Please help!

答案1

得分: 1

以下是翻译好的部分:

在.NET 7中,你可以使用UTF-8字面量创建ReadOnlySpan<byte>

class Consts
{
	public static ReadOnlySpan<byte> Delim => "\n"u8;
}

或者使用Memory/ReadOnlyMemory

public class Consts
{
	public static ReadOnlyMemory<int> Type { get; } = new []{1};
}

然后可以这样使用:

ReadOnlySpan<int> span = Consts.Type.Span;

或者将上述方法放入方法/表达式主体属性中:

class Consts
{
	private static readonly byte[] _delim = { (byte)'\n' };
	public static ReadOnlySpan<byte> Delim => _delim;
}

示例

英文:

You can create ReadOnlySpan&lt;byte&gt; with UTF-8 literal in .NET 7:

class Consts
{
	public static ReadOnlySpan&lt;byte&gt; Delim =&gt; &quot;\n&quot;u8;
}

Or use Memory/ReadOnlyMemory:

public class Consts 
{
	public static ReadOnlyMemory&lt;int&gt; Type { get; } = new []{1};
}

And usage:

ReadOnlySpan&lt;int&gt; span = Consts.Type.Span;

Or decorate aforementioned approach into method/expression bodied property:

class Consts
{
	private static readonly byte[] _delim = { (byte)&#39;\n&#39; };
	public static ReadOnlySpan&lt;byte&gt; Delim =&gt; _delim;
}

Demo

huangapple
  • 本文由 发表于 2023年2月18日 16:34:11
  • 转载请务必保留本文链接:https://go.coder-hub.com/75492129.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定