_lastBlockIndex & _lastItemIndex fields added for performance gain. Tiny cleanup.
This commit is contained in:
1 parent
9db490d8e9
commit
032908bc7d
1 file changed
+45
-7
@@ -12,6 +12,8 @@ namespace Recyclable.Collections
|
|||||||
private static readonly IEqualityComparer<T> _equalityComparer = EqualityComparer<T>.Default;
|
private static readonly IEqualityComparer<T> _equalityComparer = EqualityComparer<T>.Default;
|
||||||
|
|
||||||
private int _blockSize;
|
private int _blockSize;
|
||||||
|
private int _lastBlockIndex;
|
||||||
|
private int _lastItemIndex;
|
||||||
protected T[][] _memoryBlocks;
|
protected T[][] _memoryBlocks;
|
||||||
|
|
||||||
private long _capacity;
|
private long _capacity;
|
||||||
@@ -35,14 +37,25 @@ namespace Recyclable.Collections
|
|||||||
|
|
||||||
private static void RemoveAt(RecyclableList<T> list, long index)
|
private static void RemoveAt(RecyclableList<T> list, long index)
|
||||||
{
|
{
|
||||||
long oldCount = list._longCount;
|
long oldCountMinus1 = list._longCount - 1;
|
||||||
long oldCountMinus1 = oldCount - 1;
|
|
||||||
if (index != oldCountMinus1)
|
if (index != oldCountMinus1)
|
||||||
{
|
{
|
||||||
ThrowArgumentOutOfRangeException();
|
ThrowArgumentOutOfRangeException();
|
||||||
}
|
}
|
||||||
|
|
||||||
list._longCount--;
|
list._longCount--;
|
||||||
|
switch (list._lastItemIndex)
|
||||||
|
{
|
||||||
|
case 0:
|
||||||
|
list._lastBlockIndex--;
|
||||||
|
list._lastItemIndex = list._blockSize;
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
list._lastItemIndex--;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
int blockSize = list._blockSize;
|
int blockSize = list._blockSize;
|
||||||
if ((list._capacity * blockSize) - oldCountMinus1 == blockSize)
|
if ((list._capacity * blockSize) - oldCountMinus1 == blockSize)
|
||||||
{
|
{
|
||||||
@@ -216,15 +229,19 @@ namespace Recyclable.Collections
|
|||||||
|
|
||||||
public void Add(T item)
|
public void Add(T item)
|
||||||
{
|
{
|
||||||
int blockSize = _blockSize;
|
long requiredCapacity = _longCount + 1;
|
||||||
long oldCount = _longCount;
|
|
||||||
long requiredCapacity = oldCount + 1;
|
|
||||||
if (_capacity < requiredCapacity)
|
if (_capacity < requiredCapacity)
|
||||||
{
|
{
|
||||||
_ = EnsureCapacity(requiredCapacity);
|
_ = EnsureCapacity(requiredCapacity);
|
||||||
}
|
}
|
||||||
|
|
||||||
_memoryBlocks[(int)(oldCount / blockSize)][(int)(oldCount % blockSize)] = item;
|
_memoryBlocks[_lastBlockIndex][_lastItemIndex++] = item;
|
||||||
|
if (_lastItemIndex == _blockSize)
|
||||||
|
{
|
||||||
|
_lastBlockIndex++;
|
||||||
|
_lastItemIndex = 0;
|
||||||
|
}
|
||||||
|
|
||||||
_longCount++;
|
_longCount++;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -261,6 +278,8 @@ namespace Recyclable.Collections
|
|||||||
}
|
}
|
||||||
|
|
||||||
_longCount = targetCapacity;
|
_longCount = targetCapacity;
|
||||||
|
_lastBlockIndex = targetBlockIdx - 1;
|
||||||
|
_lastItemIndex = targetItemIdx;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void AddRange(in List<T> items)
|
public void AddRange(in List<T> items)
|
||||||
@@ -296,6 +315,8 @@ namespace Recyclable.Collections
|
|||||||
}
|
}
|
||||||
|
|
||||||
_longCount = targetCapacity;
|
_longCount = targetCapacity;
|
||||||
|
_lastBlockIndex = targetBlockIdx - 1;
|
||||||
|
_lastItemIndex = targetItemIdx;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void AddRange(in IList<T> items)
|
public void AddRange(in IList<T> items)
|
||||||
@@ -331,6 +352,8 @@ namespace Recyclable.Collections
|
|||||||
}
|
}
|
||||||
|
|
||||||
_longCount = targetCapacity;
|
_longCount = targetCapacity;
|
||||||
|
_lastBlockIndex = targetBlockIdx - 1;
|
||||||
|
_lastItemIndex = targetItemIdx;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void AddRange(IEnumerable<T> source, int growByCount = RecyclableDefaults.MinPooledArrayLength)
|
private void AddRange(IEnumerable<T> source, int growByCount = RecyclableDefaults.MinPooledArrayLength)
|
||||||
@@ -363,7 +386,7 @@ namespace Recyclable.Collections
|
|||||||
long oldLongCount = _longCount;
|
long oldLongCount = _longCount;
|
||||||
int blockSize = _blockSize;
|
int blockSize = _blockSize;
|
||||||
int targetItemIdx = (int)(oldLongCount % blockSize);
|
int targetItemIdx = (int)(oldLongCount % blockSize);
|
||||||
int targetBlockIdx = (int)(targetItemIdx / blockSize) + (targetItemIdx > 0 ? 1 : 0);
|
int targetBlockIdx = targetItemIdx / blockSize + (targetItemIdx > 0 ? 1 : 0);
|
||||||
|
|
||||||
Span<T[]> memoryBlocksSpan;
|
Span<T[]> memoryBlocksSpan;
|
||||||
Span<T> blockArraySpan;
|
Span<T> blockArraySpan;
|
||||||
@@ -396,6 +419,8 @@ namespace Recyclable.Collections
|
|||||||
}
|
}
|
||||||
|
|
||||||
_longCount = targetItemIdx;
|
_longCount = targetItemIdx;
|
||||||
|
_lastBlockIndex = targetBlockIdx - 1;
|
||||||
|
_lastItemIndex = targetItemIdx;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -447,6 +472,8 @@ namespace Recyclable.Collections
|
|||||||
}
|
}
|
||||||
|
|
||||||
_longCount = targetItemIdx;
|
_longCount = targetItemIdx;
|
||||||
|
_lastBlockIndex = targetBlockIdx - 1;
|
||||||
|
_lastItemIndex = targetItemIdx;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void Clear()
|
public void Clear()
|
||||||
@@ -460,6 +487,8 @@ namespace Recyclable.Collections
|
|||||||
}
|
}
|
||||||
|
|
||||||
_capacity = 0;
|
_capacity = 0;
|
||||||
|
_lastBlockIndex = 0;
|
||||||
|
_lastItemIndex = 0;
|
||||||
_longCount = 0;
|
_longCount = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -477,6 +506,15 @@ namespace Recyclable.Collections
|
|||||||
{
|
{
|
||||||
_memoryBlocks[index].ReturnToPool(_blockArrayPool);
|
_memoryBlocks[index].ReturnToPool(_blockArrayPool);
|
||||||
_capacity -= _blockSize;
|
_capacity -= _blockSize;
|
||||||
|
int lastBlockIndex = _lastBlockIndex;
|
||||||
|
if (lastBlockIndex == index)
|
||||||
|
{
|
||||||
|
_lastItemIndex = 0;
|
||||||
|
}
|
||||||
|
else if (lastBlockIndex > index)
|
||||||
|
{
|
||||||
|
_lastBlockIndex--;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void RemoveAt(int index) => RemoveAt(this, index);
|
public void RemoveAt(int index) => RemoveAt(this, index);
|
||||||
|
|||||||
Reference in new issue
Block a user