目录
[三、代码示例(Visual Studio控制台应用)](#三、代码示例(Visual Studio控制台应用))
[三、List<> 代码示例(Visual Studio控制台应用)](#三、List<> 代码示例(Visual Studio控制台应用))
一、ArrayList数组
一、简单介绍
ArrayList 是C#中动态数组 的实现,属于System.Collections命名空间,用于存储可变长度 的任意类型元素(本质是object类型集合)。与固定长度的Array不同,ArrayList会自动扩容,适合元素数量不确定的场景。++一个ArrayList对象额可以存储整形、字符串、对象、数组等;但是像 int[] 这种Array数组,一旦创建好后,不能后续添加元素 数组长度固定,并且一个数组对象只能存储一种类型的元素。++ ArrayList 弊端:++取出的元素是object类型++,使用时必须对其进行强制转换。
二、ArrayList数组声明与初始化模板
|-----------------|------------------------------------------|-------------------------------------------|
| 初始化方式 | 模板代码 | 说明 |
| 默认容量(推荐) | ArrayList list = new ArrayList(); | 默认初始容量为0,首次添加元素时扩容至10,后续自动按当前容量的2倍扩容。 |
| 指定初始容量 | ArrayList list = new ArrayList(10); | 初始容量为10,减少扩容次数,提升性能。 |
| 从现有数组/集合初始化 | ArrayList list = new ArrayList(现有数组/集合); | 将数组或ICollection集合的元素直接导入ArrayList。 |
三、代码示例(Visual Studio控制台应用)
static void Main()
{
// 1. 创建并初始化ArrayList(从数组导入)
int[] intArray = { 1, 2, 3 };
ArrayList list = new ArrayList(intArray); // 从int数组初始化
list.Add("Hello"); // 添加字符串(ArrayList支持混合类型)
list.Add(true); // 添加布尔值
// 2. 访问与修改元素(需强制类型转换,因为存储的是object)
Console.WriteLine("修改前第一个元素:" + (int)list[0]); // 输出:1
list[0] = 100; // 修改第一个元素
Console.WriteLine("修改后第一个元素:" + (int)list[0]); // 输出:100
// 3. 插入与删除元素
list.Insert(1, "插入的元素"); // 在索引1处插入字符串
list.RemoveAt(3); // 删除索引3的元素(原数组的3被移除)
// 4. 遍历ArrayList
Console.WriteLine("\n遍历ArrayList元素:");
foreach (object item in list)
{
Console.WriteLine(item); // 输出:100、插入的元素、2、Hello、true
}
// 5. 转换为数组(ToArray方法)
object[] objArray = list.ToArray();
Console.WriteLine("\n转换为object数组后:");
foreach (var item in objArray)
{
Console.WriteLine(item);
}
// 6. 检查元素是否存在
bool hasHello = list.Contains("Hello");
Console.WriteLine("\n是否包含\"Hello\"?" + hasHello); // 输出:True
}
四、ArrayList常用方法
|-----------------------------------|----------------------------|-------------------------------------|
| 方法名 | 用途说明 | 示例代码 |
| Add(object) | 在末尾添加元素,返回元素索引 | list.Add(5) |
| AddRange(ICollection) | 批量添加集合/数组元素到末尾 | list.AddRange(new int[] {6,7}) |
| Insert(int, object) | 在指定索引值处插入元素(索引需≤当前Count) | list.Insert(2, "插入项") |
| Remove(object) | 移除首个匹配的元素,返回是否成功 | bool removed = list.Remove("Hello") |
| RemoveAt(object) | 移除指定索引值的元素 | list.RemoveAt(0) |
| RemoveRange(startIndex,count) | 从指定元素索引值位置,移除指定个数元素 | list.RemoveRange(0,3) |
| Contains(object) | 检查元素是否存在,返回布尔值 | bool exists = list.Contains(100) |
| IndexOf(object) | 查找元素首次出现的索引值,未找到返回-1 | int index = list.IndexOf("插入项") |
| Sort() | 对数组元素顺序排序(默认升序排序) | list.Sort() |
| Reverse() | 对数组元素进行倒序处理 | list.Reverse() |
| ToArray() | 将ArrayList动态数组转换成Array数组 | list.ToArray() |
| Count() | 获取数组的元素个数 | list.Count() |
| Clear() | 清空所有元素,容量保留 | list.Clear() |
五、注意事项
-
装箱与拆箱性能问题
ArrayList存储的是object类型 ,值类型(如int、bool)会触发装箱 (值类型转object),读取时触发拆箱(object转值类型),频繁操作会严重影响性能。 -
类型不安全
由于允许存储任意类型元素,若混合存储不同类型(如
int和string),排序或类型转换时易抛出运行时异常。泛型List<T>通过强类型约束避免此问题。 -
线程不安全
ArrayList默认线程不安全。
-
扩容机制
当元素数量超过当前容量时,ArrayList会自动扩容为当前容量的2倍(默认初始容量10,首次扩容至10,后续每次翻倍)。若提前知道元素数量,建议初始化时指定容量以减少扩容次数。
-
索引边界
插入元素时,索引需≤当前Count ,否则抛出ArgumentOutOfRangeException。例如,Count为3时,只能插入到索引0~2的位置。
二、List数组
一、简单介绍
List<T> 是 C# 中最常用的泛型动态集合 ,用于存储相同类型 的元素,支持动态扩容 和丰富的操作方法 ,替代传统数组(Array)的局限性(如固定大小)。同时,List数组的方法和ArrayList数组相似,区别在于List数组可以指定类型进行存储,且存储一种数据类型,取出时不用强制转换,能保证数据类型安全。
- 核心特点 :
- 类型安全:编译时检查元素类型,避免装箱/拆箱(值类型)。
- 动态大小:自动扩容(默认初始容量为4,每次扩容翻倍)。
- 丰富方法:内置添加、删除、查找、排序等操作。
二、List数组声明与初始化模板
方式1 :空List,指定类型
List<T> list = new List<T>();
方式2 :初始容量(优化性能,避免频繁扩容)
List<T> list = new List<T>(capacity);
方式3 :用集合初始化器
List<T> list = new List<T> { item1, item2, ... };
方式4 :从数组转换
List<T> list = new List<T>(existingArray);
示例:
List<string> names = new List<string> { "Alice", "Bob" };
List<int> numbers = new List<int>(new int[] { 1, 2, 3 });
三、List<> 代码示例**(Visual Studio控制台应用)**
static void Main()
{
// 1. 创建并初始化
List List<string> fruits = new List<string> { "Apple", "Banana" };
// 2. 添加元素
fruits.Add("Cherry");
fruits.AddRange(new string[] { "Date", "Elderberry" }); // 添加多个元素
// 3. 访问元素(通过索引,与数组类似)
Console.WriteLine(fruits[0]); // 输出: Apple
// 4. 遍历List
foreach (string fruit in fruits)
{
Console.WriteLine(fruit);
}
// 5. 查找元素
if (fruits.Contains("Banana"))
{
Console.WriteLine("Found Banana at index: " + fruits.IndexOf("Banana"));
}
// 6. 删除元素
fruits.Remove("Cherry"); // 删除指定元素
fruits.RemoveAt(0); // 删除索引0的元素
// 7. 转换为数组
string[] fruitArray = fruits.ToArray();
}
四、List常用方法
|-------------------------------------------|----------------------------------|--------------------------------------------------|
| 方法名 | 描述 | 示例代码 |
| Add(T item) | 添加单个元素到末尾 | fruits.Add("Fig") |
| AddRange(IEnumerable<T> collection) | 添加多个元素 | fruits.AddRange(new[] { "Grape", "Honeydew" }) |
| Remove(T item) | 删除第一个匹配的元素 | fruits.Remove("Banana") |
| RemoveAt(int index) | 删除指定索引值的元素 | fruits.RemoveAt(1) |
| RemoveAll(条件) | 删除满足条件的所有元素 | fruits.RemoveAll() |
| Contains(T item) | 判断是否包含元素 | bool hasApple = fruits.Contains("Apple") |
| IndexOf(T item) | 返回元素的索引,不存在则-1, | int index = fruits.IndexOf("Date") |
| Count | 获取元素个数(属性,非方法) | int count = fruits.Count |
| Sort() | 对元素排序(默认升序) | fruits.Sort() |
| ToArray() | 转换为Array数组 | string[] arr = fruits.ToArray() |
| Max() | 数组序列元素当中的最大值 | list.Max() |
| Skip(int count) | 跳过指定个数元素 返回剩余 | int[] list2 = list.Skip(1).ToArray() |
| Sum() | 对所有元素求和 | list.Sum() |
| Concat(IEnumerable<T> collection) | 拼接两个数组,返回新数组,新数组包含两个数组的所有元素 | list.Concat(new int[] { 1, 2, 3}) |
| Average() | 求数组序列中所有元素的平均值 | list.Average() |
| Any(条件) | 是否存在满足条件的元素,只要存在满足条件的元素 => true | list.Any(v => v > 66) (Lambda表达式) |
| Insert(int index,item) | 插入数据,在数组指定索引值处,添加元素 | list.Insert(1, 10) |
| Clear() | 清空所有元素 | fruits.Clear() |
五、注意事项
- 命名空间 :必须引用
System.Collections.Generic,否则无法识别List<T>。 - 性能优化 :
- 初始化时指定初始容量 (如
new List<int>(100)),避免频繁扩容(每次扩容会复制现有元素)。 - 大批量添加元素时,优先使用
AddRange而非多次Add(减少方法调用开销)。
- 初始化时指定初始容量 (如
- 线程安全 :
List<T>不是线程安全的。 - 值类型 vs 引用类型 :
- 存储值类型 (如
int、struct)时,元素直接存储在List中;存储引用类型 (如class)时,存储的是对象引用。 - 修改引用类型元素的属性会影响List中的元素(因为指向同一对象)。
- 存储值类型 (如
- 避免越界 :访问索引前需检查
index < list.Count,否则会抛出ArgumentOutOfRangeException。
三、ArrayList数组和List数组的区别及优缺点
一、区别对比
|------|-------------------------------------------------|------------------------------------------|
| 对比维度 | ArrayList | List<T> |
| 类型安全 | 非泛型集合 ,存储object类型,需手动类型转换,存在运行时类型错误风险 | 泛型集合 ,指定T为元素类型,编译时类型检查,无类型转换错误 |
| 性能表现 | 存储值类型时会触发装箱/拆箱操作,性能损耗较大 | 直接存储指定类型,无装箱/拆箱,性能更优 |
| 灵活性 | 可存储任意类型对象,无需提前声明 | 仅能存储T类型对象,类型固定 |
二、ArrayList的优缺点
- 优点 :
- 无需指定元素类型,可动态存储任意对象(如混合存储int、string、自定义类)
- 缺点 :
- 类型不安全:取出元素时需强制转换
- 性能损耗:值类型(如int、double)的装箱/拆箱操作会增加内存开销和CPU负担
- 缺乏泛型方法支持 :无法直接使用
Find、Sort等泛型扩展方法
三、List<T>的优缺点
- 优点 :
- 强类型安全:编译时即检查元素类型,避免运行时错误
- 高性能 :直接操作
T类型,无装箱/拆箱,尤其适合大量数据处理 - 丰富的泛型方法 :支持
List.Find(Predicate<T>)、List.Sort(Comparison<T>)等便捷操作 - LINQ友好 :可直接结合LINQ进行复杂查询(如
list.Where(x => x.Age > 18))
- 缺点 :
- 类型固定,无法存储非
T类型的对象(如需存储多种类型需定义为List<object>
- 类型固定,无法存储非