65.9K
CodeProject 正在变化。 阅读更多。
Home

C# 的简单不可变 ArrayList

starIconstarIcon
emptyStarIcon
starIcon
emptyStarIconemptyStarIcon

2.44/5 (9投票s)

2007年11月21日

CPOL

2分钟阅读

viewsIcon

40358

downloadIcon

109

一个 ArrayList 容器包装类,允许在程序的早期阶段用数据填充表,然后使其成为只读(不可变)以供后续使用。

引言

软件开发人员有时可能需要一个容器类,例如 ArrayList,该容器类可以在程序的早期阶段用数据填充,然后使其成为只读(不可变)以供后续使用。这不能仅通过属性或成员对象访问修饰符来实现。即使某些类提供了对其 ArrayList 成员对象的只读访问权限,ArrayList 的内容仍然可以更改,即使 ArrayList 本身无法更改。

不可变 ArrayList 是一个混合 ArrayList 容器,其中

- 内部成员 ArrayList 永远无法直接供用户访问,以防止他们修改接口之外的内容。

- 只能通过 Add () 方法将项目添加到集合中,并且只能在调用 SetReadOnly () 方法之前。一旦调用该方法,ArrayList 便是不可变的。

- 不可变性通过异常抛出和 Debug.Assert 测试(因为这是一个设计问题)来强制执行,当程序在调试模式下运行时。因此,如果用户尝试在 p_isReadOnlyFlag 为 true 后调用 Add () 等方法,则 ImmutableArrayList 对象在调试模式下运行时会抛出断言错误,或者在发布模式下抛出 InvalidOperationException。

下载 ImmutableArrayListTest.zip - 8.3 KB

背景

.NET 提供了使用以下构造创建 ArrayList 的只读副本的功能

ArrayList myAL = new ArrayList ();
...
ArrayList myReadOnlyAL = ArrayList.ReadOnly (myAL)

但是现在您需要管理两个对象,并且必须为制作已经存在的容器的新副本付费。使用 ImmutableArrayList 类,您仍然只有一个容器对象,因为您没有创建任何额外的副本。 ImmutableArrayList 类本质上充当 ArrayList 的只读接口包装器。 此外,您可以调整其界面以满足您的需求(也许您希望在某些条件下使 ReadOnly 标志可逆)。

使用代码

可以将 ImmutableArrayList 类文件直接添加到项目或 dll 库项目中。用户有责任将命名空间更改为适合其项目的内容。

using System;
using System.Threading;

namespace ImmutableArrayListTest
{
  class Program
  {
    static void Main (string[] args)
    {
      ImmutableArrayList ial = new ImmutableArrayList ();

      /// Objects can be added to the ImmutableArrayList
      /// iht until it is made read-only:

      ial.Add ("apples");
      ial.Add ("oranges");
      ial.Add ("peaches");

      ial.SetReadOnly (); /// Make ial Immutable

      try
      {
        ial.Add ("plums"); /// will throw an exception
      }
      catch
      {
        Console.WriteLine ("could not add 'plums' to ial");

        Thread.Sleep (5000);
      }
    }
  }
}

关注点

为了使此类在现有应用程序中更易于使用,用户可以首先创建一个常规 ArrayList 对象,并使用已创建对象的所有 ArrayList 方法和属性;然后在创建 ImmutableArrayList 时将此对象传递给 ImmutableArrayList。 一旦调用了 SetReadOnly () 方法,就无法再从 ImmutableArrayList 接口修改内部成员 ArrayList 对象的内容。

如果需要,可以在 ImmutableArrayList 接口中公开内部成员 ArrayList 的其他本机方法。但是,重要的是要理解,切勿返回内部 ArrayList 对象本身,因为这将破坏此类目的。

历史

初始版本。

© . All rights reserved.