C# 先进先出收藏,最大尺寸,无重复?
.NET似乎有很多数据结构和集合类型。它是否有一个最大尺寸且无重复的先进先出集合,或者类似的集合 例如,用于存储5个最近打开的文件。如果添加了第6个对象,则将最近添加的对象排挤出队列,以将大小保持为5,是否 它实际上不支持最大大小和无复制,但您可以从队列继承并添加这些特性 您可以通过重写Enqueue方法来实现这一点。类似的方法可能会起作用(但会抛出更合适的异常类型!): 包含类、包装类或HAS-A类可能如下所示:C# 先进先出收藏,最大尺寸,无重复?,c#,.net,data-structures,collections,C#,.net,Data Structures,Collections,.NET似乎有很多数据结构和集合类型。它是否有一个最大尺寸且无重复的先进先出集合,或者类似的集合 例如,用于存储5个最近打开的文件。如果添加了第6个对象,则将最近添加的对象排挤出队列,以将大小保持为5,是否 它实际上不支持最大大小和无复制,但您可以从队列继承并添加这些特性 您可以通过重写Enqueue方法来实现这一点。类似的方法可能会起作用(但会抛出更合适的异常类型!): 包含类、包装类或HAS-A类可能如下所示: public class QueueWrapper<T> {
public class QueueWrapper<T>
{
private Queue<T> _queue;
public void Enqueue(T item)
{
if (_queue.Count > 5)
throw new Exception();
if(this.Contains(item))
throw new Exception();
_queue.Enqueue(item);
}
//Any other methods you might want to use would also need to be exposed similarly
}
公共类队列包装器
{
专用队列;
公共无效排队(T项)
{
如果(_queue.Count>5)
抛出新异常();
如果(本文件包含(项目))
抛出新异常();
_排队。排队(项目);
}
//您可能想要使用的任何其他方法也需要类似地公开
}
看看这个:
您基本上需要一个队列
,如果您设法限制其大小并使其“索引”或“唯一”,则您可以:)
我相信围绕
字典的一点逻辑也会起作用,您将存储什么样的数据类型?字符串?您必须创建一个实现ICollection
的QueueSet
。它可以是一个包装类,包含一个集合作为备份存储。可按如下方式实施:
class QueueSet<T> : ICollection<T>
{
List<T> queue=new List<T>();
int maximumSize;
public QueueSet(int maximumSize){
if(maximumSize<0)
throw new ArgumentOutOfRangeException("maximumSize");
this.maximumSize=maximumSize;
}
public T Dequeue(){
if(queue.Count>0){
T value=queue[0];
queue.RemoveAt(0);
return value;
}
return default(T);
}
public T Peek(){
if(queue.Count>0){
return queue[0];
}
return default(T);
}
public void Enqueue(T item){
if(queue.Contains(item)){
queue.Remove(item);
}
queue.Add(item);
while(queue.Count>maximumSize){
Dequeue();
}
}
public int Count {
get {
return queue.Count;
}
}
public bool IsReadOnly {
get {
return false;
}
}
public void Add(T item)
{
Enqueue(item);
}
public void Clear()
{
queue.Clear();
}
public bool Contains(T item)
{
return queue.Contains(item);
}
public void CopyTo(T[] array, int arrayIndex)
{
foreach(T value in queue){
if(arrayIndex>=array.Length)break;
if(arrayIndex>=0){
array[arrayIndex]=value;
}
arrayIndex++;
}
}
public bool Remove(T item)
{
if(Object.Equals(item,Peek())){
Dequeue();
return true;
} else {
return false;
}
}
public IEnumerator<T> GetEnumerator()
{
return queue.GetEnumerator();
}
System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
{
return queue.GetEnumerator();
}
}
类队列集:ICollection
{
列表队列=新列表();
int最大值;
公共队列集(int maximumSize){
如果(最大尺寸0){
T值=队列[0];
queue.RemoveAt(0);
返回值;
}
返回默认值(T);
}
公共T Peek(){
如果(队列计数>0){
返回队列[0];
}
返回默认值(T);
}
公共无效排队(T项){
if(队列包含(项目)){
队列。移除(项目);
}
添加(项目);
while(queue.Count>maximumSize){
出列();
}
}
公共整数计数{
得到{
返回队列。计数;
}
}
公共图书馆是只读的{
得到{
返回false;
}
}
公共作废新增(T项)
{
排队(项目);
}
公共空间清除()
{
queue.Clear();
}
公共布尔包含(T项)
{
返回队列。包含(项);
}
public void CopyTo(T[]数组,int arrayIndex)
{
foreach(队列中的T值){
如果(arrayIndex>=array.Length)中断;
如果(数组索引>=0){
数组[arrayIndex]=值;
}
arrayIndex++;
}
}
公共布尔删除(T项)
{
if(Object.Equals(item,Peek())){
出列();
返回true;
}否则{
返回false;
}
}
公共IEnumerator GetEnumerator()
{
返回queue.GetEnumerator();
}
System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
{
返回queue.GetEnumerator();
}
}
我将此代码发布到公共域中。这是您想要的,HashQueue
,散列队列集
添加了一些线程锁,防止意外锁定。请记住,所有HashSet操作都会破坏现有队列的顺序
using System;
using System.Collections;
using System.Collections.Generic;
using System.Runtime.Serialization;
using System.Security.Permissions;
namespace ConsoleApplication
{
internal class Program
{
[Serializable]
private class HashQueue<T> : ISerializable, IDeserializationCallback, ISet<T>, ICollection<T>, IEnumerable<T>, IEnumerable
{
private int _maxCount;
private Queue<T> _queue = new Queue<T>();
private HashSet<T> _set = new HashSet<T>();
public HashQueue(int maxCount = 0)
{
if (maxCount < 0) throw new ArgumentOutOfRangeException("maxCount");
_maxCount = maxCount;
}
public bool Add(T item)
{
lock (this)
{
if (_queue.Count == _maxCount)
{
_set.Remove(_queue.Dequeue());
}
if (_set.Add(item))
{
_queue.Enqueue(item);
return true;
}
return false;
}
}
public bool Remove(T item)
{
lock (this)
{
if (object.ReferenceEquals(_queue.Peek(), item))
{
return _set.Remove(_queue.Dequeue());
}
return false;
}
}
public void Clear()
{
lock (this)
{
_set.Clear();
_queue.Clear();
}
}
public bool Contains(T item)
{
lock (this)
{
return _set.Contains(item);
}
}
public void CopyTo(T[] array, int arrayIndex)
{
lock (this)
{
_queue.CopyTo(array, arrayIndex);
}
}
public int Count
{
get
{
lock (this)
{
return _queue.Count;
}
}
}
public bool IsReadOnly
{
get
{
return false;
}
}
public void ProcessItems(Action<T> action)
{
lock (this)
{
foreach (T item in _queue)
{
action(item);
}
}
}
void ICollection<T>.Add(T item)
{
lock (this)
{
if (_queue.Count == _maxCount)
{
_set.Remove(_queue.Dequeue());
}
if (!_set.Add(item))
{
throw new ArgumentOutOfRangeException("item");
}
_queue.Enqueue(item);
}
}
public IEnumerator<T> GetEnumerator()
{
lock (this)
{
return _queue.GetEnumerator();
}
}
System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
{
lock (this)
{
return (IEnumerator)GetEnumerator();
}
}
public void OnDeserialization(object sender)
{
lock (this)
{
_set.OnDeserialization(sender);
}
}
private void RebuildQuery()
{
_queue.Clear();
foreach (T item in _set)
{
_queue.Enqueue(item);
}
}
public void ExceptWith(IEnumerable<T> other)
{
lock (this)
{
_set.ExceptWith(other);
RebuildQuery();
}
}
public void IntersectWith(IEnumerable<T> other)
{
lock (this)
{
_set.IntersectWith(other);
RebuildQuery();
}
}
public bool IsProperSubsetOf(IEnumerable<T> other)
{
lock (this)
{
return _set.IsProperSubsetOf(other);
}
}
public bool IsProperSupersetOf(IEnumerable<T> other)
{
lock (this)
{
return _set.IsProperSupersetOf(other);
}
}
public bool IsSubsetOf(IEnumerable<T> other)
{
lock (this)
{
return _set.IsSubsetOf(other);
}
}
public bool IsSupersetOf(IEnumerable<T> other)
{
lock (this)
{
return _set.IsSupersetOf(other);
}
}
public bool Overlaps(IEnumerable<T> other)
{
lock (this)
{
return _set.Overlaps(other);
}
}
public bool SetEquals(IEnumerable<T> other)
{
lock (this)
{
return _set.SetEquals(other);
}
}
public void SymmetricExceptWith(IEnumerable<T> other)
{
lock (this)
{
_set.SymmetricExceptWith(other);
RebuildQuery();
}
}
public void UnionWith(IEnumerable<T> other)
{
lock (this)
{
_set.UnionWith(other);
RebuildQuery();
}
}
[SecurityPermissionAttribute(SecurityAction.LinkDemand, Flags = SecurityPermissionFlag.SerializationFormatter)]
void ISerializable.GetObjectData(SerializationInfo info, StreamingContext context)
{
_set.GetObjectData(info, context);
}
}
private static void Main(string[] args)
{
HashQueue<int> queue = new HashQueue<int>(5);
queue.Add(1);
queue.Add(2);
queue.Add(3);
queue.Add(4);
queue.Add(5);
queue.Add(6);
queue.ProcessItems((i) => Console.Write(i));
//foreach (int i in queue)
//{
// Console.Write("{0}", i);
//}
}
}
}
使用系统;
使用系统集合;
使用System.Collections.Generic;
使用System.Runtime.Serialization;
使用System.Security.Permissions;
命名空间控制台应用程序
{
内部课程计划
{
[可序列化]
私有类哈希队列:ISerializable、IDeserializationCallback、ISet、ICollection、IEnumerable、IEnumerable
{
私有整数最大计数;
专用队列_Queue=新队列();
私有HashSet_set=新HashSet();
公共哈希队列(int maxCount=0)
{
如果(maxCount<0)抛出新ArgumentOutOfRangeException(“maxCount”);
_maxCount=maxCount;
}
公共布尔添加(T项)
{
锁(这个)
{
如果(_queue.Count==_maxCount)
{
_set.Remove(_queue.Dequeue());
}
如果(_set.Add(项目))
{
_排队。排队(项目);
返回true;
}
返回false;
}
}
公共布尔删除(T项)
{
锁(这个)
{
if(object.ReferenceEquals(_queue.Peek(),item))
{
返回_set.Remove(_queue.Dequeue());
}
返回false;
}
}
公共空间清除()
{
锁(这个)
{
_set.Clear();
_queue.Clear();
}
}
公共布尔包含(T项)
{
锁(这个)
{
返回集合包含(项目);
}
}
public void CopyTo(T[]数组,int arrayIndex)
{
锁(这个)
{
_CopyTo(数组,arrayIndex);
}
}
公共整数计数
{
得到
{
锁(这个)
{
返回_queue.Count;
}
}
}
公共图书馆是只读的
{
得到
{
using System;
using System.Collections;
using System.Collections.Generic;
using System.Runtime.Serialization;
using System.Security.Permissions;
namespace ConsoleApplication
{
internal class Program
{
[Serializable]
private class HashQueue<T> : ISerializable, IDeserializationCallback, ISet<T>, ICollection<T>, IEnumerable<T>, IEnumerable
{
private int _maxCount;
private Queue<T> _queue = new Queue<T>();
private HashSet<T> _set = new HashSet<T>();
public HashQueue(int maxCount = 0)
{
if (maxCount < 0) throw new ArgumentOutOfRangeException("maxCount");
_maxCount = maxCount;
}
public bool Add(T item)
{
lock (this)
{
if (_queue.Count == _maxCount)
{
_set.Remove(_queue.Dequeue());
}
if (_set.Add(item))
{
_queue.Enqueue(item);
return true;
}
return false;
}
}
public bool Remove(T item)
{
lock (this)
{
if (object.ReferenceEquals(_queue.Peek(), item))
{
return _set.Remove(_queue.Dequeue());
}
return false;
}
}
public void Clear()
{
lock (this)
{
_set.Clear();
_queue.Clear();
}
}
public bool Contains(T item)
{
lock (this)
{
return _set.Contains(item);
}
}
public void CopyTo(T[] array, int arrayIndex)
{
lock (this)
{
_queue.CopyTo(array, arrayIndex);
}
}
public int Count
{
get
{
lock (this)
{
return _queue.Count;
}
}
}
public bool IsReadOnly
{
get
{
return false;
}
}
public void ProcessItems(Action<T> action)
{
lock (this)
{
foreach (T item in _queue)
{
action(item);
}
}
}
void ICollection<T>.Add(T item)
{
lock (this)
{
if (_queue.Count == _maxCount)
{
_set.Remove(_queue.Dequeue());
}
if (!_set.Add(item))
{
throw new ArgumentOutOfRangeException("item");
}
_queue.Enqueue(item);
}
}
public IEnumerator<T> GetEnumerator()
{
lock (this)
{
return _queue.GetEnumerator();
}
}
System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
{
lock (this)
{
return (IEnumerator)GetEnumerator();
}
}
public void OnDeserialization(object sender)
{
lock (this)
{
_set.OnDeserialization(sender);
}
}
private void RebuildQuery()
{
_queue.Clear();
foreach (T item in _set)
{
_queue.Enqueue(item);
}
}
public void ExceptWith(IEnumerable<T> other)
{
lock (this)
{
_set.ExceptWith(other);
RebuildQuery();
}
}
public void IntersectWith(IEnumerable<T> other)
{
lock (this)
{
_set.IntersectWith(other);
RebuildQuery();
}
}
public bool IsProperSubsetOf(IEnumerable<T> other)
{
lock (this)
{
return _set.IsProperSubsetOf(other);
}
}
public bool IsProperSupersetOf(IEnumerable<T> other)
{
lock (this)
{
return _set.IsProperSupersetOf(other);
}
}
public bool IsSubsetOf(IEnumerable<T> other)
{
lock (this)
{
return _set.IsSubsetOf(other);
}
}
public bool IsSupersetOf(IEnumerable<T> other)
{
lock (this)
{
return _set.IsSupersetOf(other);
}
}
public bool Overlaps(IEnumerable<T> other)
{
lock (this)
{
return _set.Overlaps(other);
}
}
public bool SetEquals(IEnumerable<T> other)
{
lock (this)
{
return _set.SetEquals(other);
}
}
public void SymmetricExceptWith(IEnumerable<T> other)
{
lock (this)
{
_set.SymmetricExceptWith(other);
RebuildQuery();
}
}
public void UnionWith(IEnumerable<T> other)
{
lock (this)
{
_set.UnionWith(other);
RebuildQuery();
}
}
[SecurityPermissionAttribute(SecurityAction.LinkDemand, Flags = SecurityPermissionFlag.SerializationFormatter)]
void ISerializable.GetObjectData(SerializationInfo info, StreamingContext context)
{
_set.GetObjectData(info, context);
}
}
private static void Main(string[] args)
{
HashQueue<int> queue = new HashQueue<int>(5);
queue.Add(1);
queue.Add(2);
queue.Add(3);
queue.Add(4);
queue.Add(5);
queue.Add(6);
queue.ProcessItems((i) => Console.Write(i));
//foreach (int i in queue)
//{
// Console.Write("{0}", i);
//}
}
}
}