哪个更好?数组,ArrayList还是List(从性能和速度方面来看)

17 浏览
0 Comments

哪个更好?数组,ArrayList还是List(从性能和速度方面来看)

我需要快速处理我的页面。要添加的值的数量将是动态的。

以上两种方式哪一个更好?请给出一个有效的理由。

编辑:例如:

string str = "a,b,c"; //Count of the number of elements in str is not fixed
string[] arr = str.Split(',');

或者,

ArrayList al = new ArrayList();
al.Add(str.Split(','));

admin 更改状态以发布 2023年5月24日
0
0 Comments

针对“不可变”集合的数组,
List 用于可变集合。

  • “不可变”集合——只在创建时进行更改,之后进行多次读取。
  • 可变集合——随时进行多次更改

性能统计(Array vs List vs ReadonlyCollection):

       Array                List        ReadOnlyCollection         Penalties      Method
00:00:01.3932446    00:00:01.6677450    00:00:06.2444633    1 vs  1,2  vs  4,5   Generate
00:00:00.1856069    00:00:01.0291365    00:00:02.0674881    1 vs  5,5  vs 11,1   Sum
00:00:00.4350745    00:00:00.9422126    00:00:04.5994937    1 vs  2,2  vs 10,6   BlockCopy
00:00:00.2029309    00:00:00.4272936    00:00:02.2941122    1 vs  2,1  vs 11,3   Sort

源代码:

interface IMethods
{
  T Generate(int size, Func generator);
   int Sum(T items);
   T BlockCopy(T items);
   T Sort(T items);
}
class ArrayMethods:IMethods
{
  public int[] Generate(int size, Func generator)
  {
    var items = new int[size];
    for (var i = 0; i < items.Length; ++i)
      items[i] = generator(i);
    return items;
  }
  public int Sum(int[] items)
  {
    int sum = 0;
    foreach (var item in items)
      sum += item;
    return sum;
  }
  public int[] BlockCopy(int[] items)
  {
    var res = new int[items.Length / 2];
    Buffer.BlockCopy(items, items.Length / 4 * sizeof(int), res, 0, res.Length * sizeof(int));
    return res;
  }
  public int[] Sort(int[] items)
  {
    var res = new int[items.Length];
    Buffer.BlockCopy(items, 0, res, 0, items.Length * sizeof(int));
    return res;
  }
}
class ListMethods : IMethods>
{
  public List Generate(int size, Func generator)
  {
    var items = new List(size);
    for (var i = 0; i < size; ++i)
      items.Add(generator(i));
    return items;
  }
  public int Sum(List items)
  {
    int sum = 0;
    foreach (var item in items)
      sum += item;
    return sum;
  }
  public List BlockCopy(List items)
  {
    var count = items.Count / 2;
    var res = new List(count);
    var start = items.Count / 4;
    for (var i = 0; i < count; ++i)
      res.Add(items[start + i]);
    return res;
  }
  public List Sort(List items)
  {
    var res = new List(items);
    res.Sort();
    return res;
  }
}
class ReadOnlyCollectionMethods:IMethods>
{
  public ReadOnlyCollection Generate(int size, Func generator)
  {
    return new ReadOnlyCollection(Enumerable.Range(0, size).Select(generator).ToList());
  }
  public int Sum(ReadOnlyCollection items)
  {
    int sum = 0;
    foreach (var item in items)
      sum += item;
    return sum;
  }
  public ReadOnlyCollection BlockCopy(ReadOnlyCollection items)
  {
    return new ReadOnlyCollection(items.Skip(items.Count / 4).Take(items.Count / 2).ToArray());
  }
  public ReadOnlyCollection Sort(ReadOnlyCollection items)
  {
    return new ReadOnlyCollection(items.OrderBy(s => s).ToList());
  }
}
static class Program
{
  static Tuple[] CheckPerformance(IMethods methods) where T:class
  {
    var stats = new List>();
    T source = null;
    foreach (var info in new[] 
      { 
        new {Name = "Generate", Method = new Func(items => methods.Generate(10000000, i => i % 2 == 0 ? -i : i))}, 
        new {Name = "Sum", Method =  new Func(items => {Console.WriteLine(methods.Sum(items));return items;})}, 
        new {Name = "BlockCopy", Method = new Func(items => methods.BlockCopy(items))}, 
        new {Name = "Sort", Method = new Func(items => methods.BlockCopy(items))}, 
        new {Name = "Sum", Method =  new Func(items => {Console.WriteLine(methods.Sum(items));return items;})}, 
      }
     )
    {
      int count = 10;
      var stopwatch = new Stopwatch();
      stopwatch.Start();
      T res = null;
      for (var i = 0; i < count; ++i)
        res = info.Method(source);
      stopwatch.Stop();
      source = res;
      stats.Add(new Tuple(info.Name, stopwatch.Elapsed));
    }
    return stats.ToArray();
  }
  static void Main()
  {
    var arrayStats = CheckPerformance(new ArrayMethods());
    var listStats = CheckPerformance(new ListMethods());
    var rcStats = CheckPerformance(new ReadOnlyCollectionMethods());
    Console.WriteLine("       Array                List        ReadOnlyCollection         Penalties      Method");
    for(var i = 0; i < arrayStats.Length; ++i)
    {
      Console.WriteLine("{0}    {1}    {2}    1 vs {3,4:f1}  vs {4,4:f1}   {5}", arrayStats[i].Item2, listStats[i].Item2, rcStats[i].Item2, 
        listStats[i].Item2.TotalSeconds / arrayStats[i].Item2.TotalSeconds,
        rcStats[i].Item2.TotalSeconds / arrayStats[i].Item2.TotalSeconds, arrayStats[i].Item1);
    }
  }

0
0 Comments

List通常比ArrayList更优。

  • 对于值类型而言,它比较快,因为它避免了装箱。
  • 元素是强类型的。

如果你想要将列表暴露给调用者是不可变的,那么ListArrayList都支持:

List.AsReadOnly()
ArrayList.ReadOnly(ArrayList list);

你的问题问到如何在ArrayListList之间做出选择,但你的示例显示的是一个数组,两者都与之不同。

0