System.Collections的线程安全

我们认真一点会发现System.Collections名字空间中几乎所有的容器类帮助文档中都有类似下面的一段话:

ArrayList
只要集合未修改,ArrayList 就可以同时支持多个阅读器。若要保证 ArrayList 的线程安全,则必须通过由 Synchronized 方法返回的包装来执行所有操作。

Hashtable
Hashtable 是线程安全的,可由多个读取器线程或一个写入线程使用。多线程使用时,如果任何一个线程执行写入(更新)操作,它都不是线程安全的。若要支持多个编写器,如果没有任何线程在读取 Hashtable 对象,则对 Hashtable 的所有操作都必须通过 Synchronized 方法返回的包装完成。

那么这个Synchronized 静态方法究竟做了什么处理,可以让返回的对象具备多读写安全呢?和我们平时使用lock关键字锁定有什么不同吗?
Hashtable hash = Hashtable.Synchronized(new Hashtable());

用 Reflector 查看Hashtable.Synchronized方法。
[HostProtection(SecurityAction.LinkDemand, Synchronization=true)]
public static Hashtable Synchronized(Hashtable table)
{
  if (table == null)
  {
    throw new ArgumentNullException("table");
  }
  return new Hashtable.SyncHashtable(table);
}


我们发现该方法创建了一个Hashtable的子类SyncHashtable实例。
using System;
using System.Collections;
using System.Reflection;
using System.Runtime.Serialization;

[Serializable]
private class SyncHashtable : Hashtable
{
  internal SyncHashtable(Hashtable table)
    : base(false)
  {
    this._table = table;
  }

  internal SyncHashtable(SerializationInfo info, StreamingContext context)
    : base(info, context)
  {
    this._table = (Hashtable)info.GetValue("ParentTable", typeof(Hashtable));
    if (this._table == null)
    {
      throw new SerializationException(Environment.GetResourceString("Serialization_InsufficientState"));
    }
  }

  public override void Add(object key, object value)
  {
    lock (this._table.SyncRoot)
    {
      this._table.Add(key, value);
    }
  }

  public override void Clear()
  {
    lock (this._table.SyncRoot)
    {
      this._table.Clear();
    }
  }

  public override object Clone()
  {
    object obj1;
    lock (this._table.SyncRoot)
    {
      obj1 = Hashtable.Synchronized((Hashtable)this._table.Clone());
    }
    return obj1;
  }

  public override bool Contains(object key)
  {
    return this._table.Contains(key);
  }

  public override bool ContainsKey(object key)
  {
    return this._table.ContainsKey(key);
  }

  public override bool ContainsValue(object key)
  {
    bool flag1;
    lock (this._table.SyncRoot)
    {
      flag1 = this._table.ContainsValue(key);
    }
    return flag1;
  }

  public override void CopyTo(Array array, int arrayIndex)
  {
    lock (this._table.SyncRoot)
    {
      this._table.CopyTo(array, arrayIndex);
    }
  }

  public override IDictionaryEnumerator GetEnumerator()
  {
    return this._table.GetEnumerator();
  }

  public override void GetObjectData(SerializationInfo info, StreamingContext context)
  {
    if (info == null)
    {
      throw new ArgumentNullException("info");
    }
    info.AddValue("ParentTable", this._table, typeof(Hashtable));
  }

  public override void OnDeserialization(object sender)
  {
  }

  public override void Remove(object key)
  {
    lock (this._table.SyncRoot)
    {
      this._table.Remove(key);
    }
  }

  internal override KeyValuePairs[] ToKeyValuePairsArray()
  {
    return this._table.ToKeyValuePairsArray();
  }

  public override int Count
  {
    get
    {
      return this._table.Count;
    }
  }

  public override bool IsFixedSize
  {
    get
    {
      return this._table.IsFixedSize;
    }
  }

  public override bool IsReadOnly
  {
    get
    {
      return this._table.IsReadOnly;
    }
  }

  public override bool IsSynchronized
  {
    get
    {
      return true;
    }
  }

  public override object this[object key]
  {
    get
    {
      return this._table[key];
    }
    set
    {
      lock (this._table.SyncRoot)
      {
        this._table[key] = value;
      }
    }
  }

  public override ICollection Keys
  {
    get
    {
      ICollection collection1;
      lock (this._table.SyncRoot)
      {
        collection1 = this._table.Keys;
      }
      return collection1;
    }
  }

  public override object SyncRoot
  {
    get
    {
      return this._table.SyncRoot;
    }
  }

  public override ICollection Values
  {
    get
    {
      ICollection collection1;
      lock (this._table.SyncRoot)
      {
        collection1 = this._table.Values;
      }
      return collection1;
    }
  }

  protected Hashtable _table;
}
 
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值