Last active
May 25, 2020 12:16
-
-
Save mstevenson/4050130 to your computer and use it in GitHub Desktop.
Shuffle bag algorithm implemented in C#
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using UnityEngine; | |
using System.Collections; | |
using System.Collections.Generic; | |
public class ShuffleBag<T> : ICollection<T>, IList<T> | |
{ | |
private List<T> data = new List<T> (); | |
private int cursor = 0; | |
private T last; | |
public T Next () | |
{ | |
if (cursor < 1) { | |
cursor = data.Count - 1; | |
if (data.Count < 1) | |
return default(T); | |
return data[0]; | |
} | |
int grab = Mathf.FloorToInt (Random.value * (cursor + 1)); | |
T temp = data[grab]; | |
data[grab] = this.data[this.cursor]; | |
data[cursor] = temp; | |
cursor--; | |
return temp; | |
} | |
#region IList[T] implementation | |
public int IndexOf (T item) | |
{ | |
return data.IndexOf (item); | |
} | |
public void Insert (int index, T item) | |
{ | |
data.Insert (index, item); | |
} | |
public void RemoveAt (int index) | |
{ | |
data.RemoveAt (index); | |
} | |
public T this[int index] { | |
get { | |
return data [index]; | |
} | |
set { | |
data [index] = value; | |
} | |
} | |
#endregion | |
#region IEnumerable[T] implementation | |
IEnumerator<T> IEnumerable<T>.GetEnumerator () | |
{ | |
return data.GetEnumerator (); | |
} | |
#endregion | |
#region ICollection[T] implementation | |
public void Add (T item) | |
{ | |
Debug.Log (item); | |
data.Add (item); | |
cursor = data.Count - 1; | |
} | |
public int Count { | |
get { | |
return data.Count; | |
} | |
} | |
public void Clear () | |
{ | |
data.Clear (); | |
} | |
public bool Contains (T item) | |
{ | |
return data.Contains (item); | |
} | |
public void CopyTo (T[] array, int arrayIndex) | |
{ | |
foreach (T item in data) { | |
array.SetValue (item, arrayIndex); | |
arrayIndex = arrayIndex + 1; | |
} | |
} | |
public bool Remove (T item) | |
{ | |
return data.Remove (item); | |
} | |
public bool IsReadOnly { | |
get { | |
return false; | |
} | |
} | |
#endregion | |
#region IEnumerable implementation | |
IEnumerator IEnumerable.GetEnumerator () | |
{ | |
return data.GetEnumerator (); | |
} | |
#endregion | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
I found a problem! Have a look at this code:
I create a ShuffleBag with 4 values, remove one value and then I try to go through the entire bag several times...
This throws an Error on line 20.
To fix this for Remove, RemoveAt and Insert I had to set the cursor to data.Count -2 in Remove/RemoveAt and to data.Count in Insert...
Made a fork and fixed it: https://gist.github.com/col000r/6658520