在最近的 C# 12.0 和 .NET 8.0 介绍了一个新的特性:内联数组。内联数组被设计用来提升性能和内存效率。这种数据结构是把数组直接内嵌在一个结构中,这样就避免为数组单独分配堆空间,提高了引用位置性以及减少了垃圾回收的开销。
我们先来看一个例子:
using System;
using System.Runtime.CompilerServices;
[InlineArray(4)] // Specifies an inline array with 4 elements.
public struct InlineIntArray
{
public int Element;
}
public class Program
{
public static void Main()
{
InlineIntArray array = default;
// Access and modify elements like a regular array.
array[0] = 10;
array[1] = 20;
array[2] = 30;
array[3] = 40;
// Iterate over the elements
for (int i = 0; i < 4; i++)
{
Console.WriteLine(array[i]);
}
}
}
这个例子里的要点:
- [InlineArray(4)] 声明了一个和具有4个元素数组行为相似的结构
- 结构以内联方式存储数组元素,这意味着元素是结构内存的一部分
- 访问语法:使用与标准数组相同的索引语法(array[0]、array[1]等)访问元素
内联数组是在结构内部声明的固定大小数组。
与普通数组不同,内联数组位于堆栈(对于值类型)或结构内部,而不是在堆上单独分配。
在编译时已知数组大小较小的高性能情况下,这一点尤其有用。
为什么使用内联阵列?
1. 提高性能:
由于数组是结构体的一部分,因此缓存定位性更好。
减少固定大小的小型数组的堆分配开销。
2. 减少垃圾回收压力:
内联数组采用堆分配(对于值类型),避免了堆分配,从而减少了垃圾回收开销。
3. 易于使用:
简化了结构设计,适用于经常使用小型数组的情况。
比较:
特性 | 内联数组 | 普通数组 |
---|---|---|
存储方式 | 栈 | 堆 |
大小 | 在编译时固定 | 动态 |
垃圾回收 | 对于值类型,不用回收 | 是 |
性能 | 适用小型固定数组 | 增加堆开销 |
灵活性 | 硬性(大小和类型在编译时固定) | 高灵活性 |
通过以上比较,我们可以预见到内联数组比较适合这些场景:
高性能数据结构:
需要小型固定大小数组的场景,减少堆分配。
游戏开发:
常用于游戏引擎中的空间数据、物理计算或渲染管道。
嵌入式系统:
适用于对内存管理和性能要求较高的环境。
总而言之,在高性能环境中,尤其是嵌入结构体中的固定大小的小数组中,内联数组大放异彩。
发表回复