使用C#中的ArrayPool重新使用从字符串到字节数组的内存转换?

使用C#中的ArrayPool重新使用从字符串到字节数组的内存转换?,c#,.net,memory-management,garbage-collection,C#,.net,Memory Management,Garbage Collection,是否可以重新使用字符串到字节数组转换中使用的内存 应用程序必须以60fps的速度通过网络发送大型字符串。这似乎给GC带来了太大的压力。那么,是否有可能以某种方式重新使用字符串转换创建的字节数组呢 以下是我当前的序列化方法: public static byte[] SerializeJson(DrawDescriptionLayer layer) { var s = JsonConvert.SerializeObject(layer, js); return Encoding.U

是否可以重新使用字符串到字节数组转换中使用的内存

应用程序必须以60fps的速度通过网络发送大型字符串。这似乎给GC带来了太大的压力。那么,是否有可能以某种方式重新使用字符串转换创建的字节数组呢

以下是我当前的序列化方法:

public static byte[] SerializeJson(DrawDescriptionLayer layer)
{
    var s = JsonConvert.SerializeObject(layer, js);
    return Encoding.UTF8.GetBytes(s); //rent from array pool here
}
或使用流:

public static byte[] SerializeJson2(DrawDescriptionLayer layer)
{
    using (var ms = new MemoryStream())
    using (StreamWriter writer = new StreamWriter(ms, Encoding.UTF8))
    using (JsonTextWriter jsonWriter = new JsonTextWriter(writer))
    {
        JsonSerializer ser = JsonSerializer.Create(js);
        ser.Serialize(jsonWriter, layer);
        jsonWriter.Flush();
        return ms.ToArray(); //rent from array pool here
    }
}

我意识到我应该编写一个定制的二进制序列化程序,但是NeNtSoop.JSON是在方框中完成的,应用程序使用了没有序列化属性的第三方类型。

< P>如果性能和内存分配是主要的关注点,你应该强烈地考虑使用.< /P> utf8json不必同时使用slow
JsonConvert.SerializeObject
方法和分配重
UTF8.GetBytes
,而是一次完成:

public byte[]序列化JSON(DrawDescriptionLayer层)
{
返回Utf8Json.JsonSerializer.Serialize(层,Utf8Json.Resolvers.StandardResolver.Default);
}
该库针对性能和低分配进行了优化,并用于ElasticSearch推荐的.NET客户端等软件中

还要确保
DrawDescriptionLayer
是一个针对廉价JSON序列化进行了高度优化的DTO,并且不包含任何未在网络传输中使用的内容


祝你好运

我还没有在生产层面上使用它,尽管我可以考虑一些明确的用例。您可能会从这里得到更多的想法()您可能会看到使用
MemoryStream.GetBuffer()
而不是
MemoryStream.ToArray()
-前者返回流的内部缓冲区,而不是复制到新的字节数组。需要注意的是,内部缓冲区可能会大于流长度,因此您还需要传递流长度(或者使用
ArraySegment
)。@Iridium good hint,我可以将缓冲区复制到池数组中,因为流的计数是已知的。这可能会节省一次数组垃圾收集。感谢您启动Utf8Json序列化程序,它看起来很不错,但它无法序列化我的对象树,它可能没有Newtonsoft.Json那么成熟,它在我的情况下可以工作。不客气!不禁想到使用DTO来简化复杂对象树可以在CPU、GC和网络带宽上节省很多,因此强烈建议考虑。但是,如果您能够提供更多关于对象树utf8json的哪些部分正在挣扎的信息,那将是非常有帮助的。它抛出了一个异常:似乎是对字典键的过于简单的管理。