【问题标题】:Dealing with escape sequences with ReadOnlySpan<char>使用 ReadOnlySpan<char> 处理转义序列
【发布时间】:2018-07-15 07:47:26
【问题描述】:

ReadOnlySpan&lt;char&gt; 据说非常适合解析,所以我尝试使用它,但遇到了一个我不知道如何处理的用例。


我有一个命令行string,其中参数前缀- 和分隔符(空格)被转义(我知道我可以在这里引用它们但是为了这个问题让我们假设这不是一个选项)

 var str = @"foo -bar \-baz\ qux".AsMemory();

标记器应返回以下标记:

  1. foo - 命令名称
  2. bar - 参数名称
  3. -baz qux - 参数值

案例12 很简单,因为在这里我可以只使用str.Slice(i, length),但我如何创建3rd 案例并只返回一个ReadOnlySpan&lt;char&gt;Slice 方法不允许我指定多个start/length 范围,这是跳过转义字符\ 所必需的。

例子:

str.Slice((10, 4), (15, 3)); 

(10,4) = "-bar"(15,3) = " qux" 的位置

使用StringBuilder,您可以跳过几个字符,稍后再跳过Append 其他字符。我如何使用ReadOnlySpan&lt;char&gt; 获得相同的结果?

【问题讨论】:

  • Slice 方法不允许我指定多个开始/长度范围我不太明白你的意思。你能解释一下吗?此外,在这里使用 span 似乎就像用大锤击打苍蝇一样,如果你想规定分配 span 和内存很棒,但这只是一个命令行 arg,而且你似乎无论如何都必须遍历 span .
  • @TheGeneral 在这里使用 span 似乎就像用大锤击打苍蝇 - 我知道 - 在这种情况下这可能是真的但是 Sytem.Memory 包是相当新的并且你已经以某种方式开始了,所以我选择了一个非常简单的用例来使用,所以让我们暂时忘记还有其他方法;-) 多个start/lengh 我的意思是这样的str.Slice((10, 4), (15, 3));,其中(10,4) = "-bar"(15,3) = " qux" .

标签: c# parsing system.memory


【解决方案1】:

Span/ReadOnlySpan 是一个连续的内存块。它不能包含多个范围。这种设计是性能所必需的。 Span/ReadOnlySpan 应该与数组大致一样快。数组速度很快,因为它们是连续的内存块,没有进一步的抽象。

如果不分配新字符串,我没有办法做到这一点。您可以对所有连续的子字符串使用Span/ReadOnlySpan,但您的解析问题似乎不适合使用 span 来存储结果。

【讨论】:

  • 你写的是Span,但问题是关于ReadOnlySpan。对于ReadOnlySpan,你的答案是正确的。如果您确实想提及Span,还有另一种选择:就地修改缓冲区。
  • @hvd 就地写入是一个好点,尽管就地修改字符串似乎非常不安全。谁知道打破了什么。他可以使用char[]
  • @hvd @usr 所以我猜想使用System.Memory 无法解析任何涉及转义序列(html、json、csv...等)的内容,对吧?
  • 解析通常变得更容易或更高效。存储解析的结果是另一回事。你是对的,转义序列使得在这里使用 Span 变得不可能。
【解决方案2】:

看看: https://github.com/nemesissoft/Nemesis.TextParsers

更准确地说是: TokenSequence.cs

用法:

var tokens = "ABC|CD\|E".AsSpan().Tokenize('|', '\\', false); //no allocation. Result in 2 elements: "ABC", "CD\|E". 

通过以下方式消费:

var result = new List<string>();
foreach (var part in tokens)
     result.Add(part.ToString());

可以通过以下方式取消转义: ParsedSequence.cs

SpanParserHelper.UnescapeCharacter()

希望对你有帮助

【讨论】:

猜你喜欢
  • 1970-01-01
  • 2018-11-11
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-04-06
  • 2013-01-20
  • 1970-01-01
相关资源
最近更新 更多