C# ArrayPool 详解

ArrayPool<T> 是 .NET 中的一个高性能数组池,用于减少内存分配和垃圾回收的开销。

基本用法

// 基本使用方式
public void BasicUsage()
{
    // 从共享池获取数组
    char[] array = ArrayPool<char>.Shared.Rent(100);
    
    try
    {
        // 使用数组
        // ... 业务逻辑 ...
    }
    finally
    {
        // 归还数组到池中
        ArrayPool<char>.Shared.Return(array);
    }
}

高级用法

// 创建自定义数组池
public class CustomArrayPoolExample
{
    private readonly ArrayPool<byte> _customPool;
    
    public CustomArrayPoolExample()
    {
        // 创建最大数组长度为1024,最多保留10个数组的池
        _customPool = ArrayPool<byte>.Create(maxArrayLength: 1024, maxArraysPerBucket: 10);
    }
    
    public void UseCustomPool()
    {
        // 从自定义池租用数组
        byte[] buffer = _customPool.Rent(256);
        
        try
        {
            // 使用数组
            // ... 业务逻辑 ...
        }
        finally
        {
            // 清除敏感数据
            Array.Clear(buffer, 0, buffer.Length);
            // 归还数组
            _customPool.Return(buffer);
        }
    }
}

性能优化示例

public class HighPerformanceExample
{
    private static readonly ArrayPool<char> _charPool = ArrayPool<char>.Shared;
    
    public string ProcessLargeString(string input)
    {
        char[] buffer = _charPool.Rent(input.Length * 2);
        
        try
        {
            // 处理字符串
            int resultLength = ProcessBuffer(input, buffer);
            return new string(buffer, 0, resultLength);
        }
        finally
        {
            _charPool.Return(buffer);
        }
    }
    
    private int ProcessBuffer(string input, char[] buffer)
    {
        // 处理逻辑
        return input.Length;
    }
}

最佳实践

使用 using 语句

public string SafeArrayPoolUsage(int size)
{
    using var owner = MemoryPool<char>.Shared.Rent(size);
    var memory = owner.Memory;
    // 使用 memory
    return memory.ToString();
}

/**

需要直接数组操作,选择 ArrayPool
需要安全性保证,选择 MemoryPool
异步操作推荐 MemoryPool
高性能场景推荐 ArrayPool
*/

避免常见错误

// 错误示例 - 不要这样做
var array = ArrayPool<int>.Shared.Rent(100);
// 忘记返回数组 - 内存泄漏!

// 正确示例
var array = ArrayPool<int>.Shared.Rent(100);
try
{
    // 使用数组
}
finally
{
    ArrayPool<int>.Shared.Return(array);
}

使用场景

大数据处理场景

public class BigDataProcessor
{
    private readonly ArrayPool<byte> _pool = ArrayPool<byte>.Shared;

    public void ProcessLargeData(Stream stream)
    {
        byte[] buffer = _pool.Rent(81920); // 80KB 缓冲区
        try
        {
            while (stream.Read(buffer, 0, buffer.Length) > 0)
            {
                // 处理数据
            }
        }
        finally
        {
            _pool.Return(buffer);
        }
    }
}

图像处理

public class ImageProcessor
{
    private readonly ArrayPool<byte> _pixelPool = ArrayPool<byte>.Shared;

    public void ProcessImage(Bitmap bitmap)
    {
        byte[] pixels = _pixelPool.Rent(bitmap.Width * bitmap.Height * 4);
        try
        {
            // 处理图像像素
        }
        finally
        {
            _pixelPool.Return(pixels);
        }
    }
}

网络通信

public class NetworkHandler
{
    private readonly ArrayPool<byte> _networkPool = ArrayPool<byte>.Shared;

    public async Task HandleNetworkData(NetworkStream stream)
    {
        byte[] buffer = _networkPool.Rent(4096);
        try
        {
            await stream.ReadAsync(buffer, 0, buffer.Length);
            // 处理网络数据
        }
        finally
        {
            _networkPool.Return(buffer);
        }
    }
}

字符串处理

public class StringProcessor
{
    private readonly ArrayPool<char> _charPool = ArrayPool<char>.Shared;

    public string ProcessLargeString(string input)
    {
        char[] buffer = _charPool.Rent(input.Length * 2);
        try
        {
            // 字符串处理逻辑
            return new string(buffer, 0, input.Length);
        }
        finally
        {
            _charPool.Return(buffer);
        }
    }
}

高频临时数组

public class HighFrequencyProcessor
{
    private readonly ArrayPool<int> _intPool = ArrayPool<int>.Shared;

    public void ProcessData()
    {
        int[] tempArray = _intPool.Rent(1000);
        try
        {
            // 高频临时计算
        }
        finally
        {
            _intPool.Return(tempArray, clearArray: true); // 清除敏感数据
        }
    }
}

 适合场景

频繁创建和销毁数组的场景
- 大型数组操作
- 需要临时缓冲区的操作
- 性能敏感的应用

不适合场景

- 长期持有数组的场景
- 数组大小不固定频繁变化
- 小型数组(小于16字节)
- 生命周期不确定的场景

性能优化建议

- 使用 using 语句确保返回
- 适当设置 clearArray 参数
- 选择合适的数组大小
- 避免过度池化

注意事项

- 必须及时返回数组
- 注意线程安全
- 不要修改已返回的数组
- 考虑内存占用

ArrayPool 是一个强大的性能优化工具,但需要在合适的场景下使用,并注意正确的使用方式

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值