Skip to content

Commit

Permalink
Revert and fix out of bound RobinHoodMap.cs
Browse files Browse the repository at this point in the history
  • Loading branch information
Wsm2110 committed Dec 27, 2024
1 parent 5e9b947 commit 6e937dc
Show file tree
Hide file tree
Showing 4 changed files with 22 additions and 16 deletions.
10 changes: 5 additions & 5 deletions src/Concurrent/CMap.cs
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ public IEnumerable<TKey> Keys
get
{
var table = _table;
for (int i = 0; i < table.Entries.Length; i++)
for (int i = table.Entries.Length - 1; i >= 0; i--)
{
var entry = table.Entries[i];
if (entry.Meta > -1)
Expand All @@ -60,7 +60,7 @@ public IEnumerable<TValue> Values
get
{
var table = _table;
for (int i = 0; i < table.Entries.Length; i++)
for (int i = table.Entries.Length - 1; i >= 0; i--)
{
var entry = table.Entries[i];
if (entry.Meta > -1)
Expand All @@ -79,7 +79,7 @@ public IEnumerable<KeyValuePair<TKey, TValue>> Entries
get
{
var table = _table;
for (int i = 0; i < table.Entries.Length; i++)
for (int i = table.Entries.Length - 1; i >= 0; i--)
{
var entry = table.Entries[i];
if (entry.Meta > -1)
Expand Down Expand Up @@ -491,7 +491,7 @@ public bool Remove(TKey key)
// This means that when you perform an Interlocked operation, it guarantees that any changes made to other variables(not just the variable involved in the Interlocked operation) are also visible to other threads.
// Note this also means we dont need any explicit memorybarriers.
// This code, using Interlocked operations, will also work correctly on ARM architectures without needing additional explicit memory barriers.The memory ordering and visibility are managed by the Interlocked methods.
_counter.Decrement();
_counter.Decrement();
// Remove operation succeeded
return true;
}
Expand Down Expand Up @@ -568,7 +568,7 @@ public bool Remove(TKey key, out TValue value)
entry.Value = default;
// Setting tombstone will release the lock
entry.Metadata = _tombstone;

// _counter.Decrement() uses a Interlocked.Decrement() which provides a full memory fence, meaning they ensure all preceding memory writes are completed and visible to other threads before the Interlocked operation completes.
// This means that when you perform an Interlocked operation, it guarantees that any changes made to other variables(not just the variable involved in the Interlocked operation) are also visible to other threads.
// Note this also means we dont need any explicit memorybarriers.
Expand Down
6 changes: 3 additions & 3 deletions src/DenseMap.cs
Original file line number Diff line number Diff line change
Expand Up @@ -80,7 +80,7 @@ public IEnumerable<KeyValuePair<TKey, TValue>> Entries
{
get
{
for (int i = 0; i < _controlBytes.Length; ++i)
for (int i = _controlBytes.Length - 1; i >= 0; --i)
{
if (_controlBytes[i] >= 0)
{
Expand All @@ -107,7 +107,7 @@ public IEnumerable<TKey> Keys
{
get
{
for (int i = 0; i < _controlBytes.Length; ++i)
for (int i = _controlBytes.Length - 1; i >= 0; --i)
{
if (_controlBytes[i] >= 0)
{
Expand All @@ -133,7 +133,7 @@ public IEnumerable<TValue> Values
{
get
{
for (int i = 0; i < _controlBytes.Length; ++i)
for (int i = _controlBytes.Length - 1; i >= 0; --i)
{
if (_controlBytes[i] >= 0)
{
Expand Down
17 changes: 12 additions & 5 deletions src/RobinHoodMap.cs
Original file line number Diff line number Diff line change
Expand Up @@ -82,7 +82,7 @@ public IEnumerable<KeyValuePair<TKey, TValue>> Entries
{
get
{
for (int i = 0; i< _meta.Length; ++i)
for (int i = _meta.Length - 1; i >= 0; --i)
{
var meta = _meta[i];
if (meta is not 0)
Expand All @@ -109,7 +109,7 @@ public IEnumerable<TKey> Keys
{
get
{
for (int i = 0; i < _meta.Length; ++i)
for (int i = _meta.Length - 1; i >= 0; --i)
{
var meta = _meta[i];
if (meta > 0)
Expand All @@ -136,7 +136,7 @@ public IEnumerable<TValue> Values
{
get
{
for (int i = 0; i < _meta.Length; ++i)
for (int i = _meta.Length - 1; i >= 0; --i)
{
var meta = _meta[i];
if (meta is not 0)
Expand Down Expand Up @@ -259,6 +259,14 @@ public bool Emplace(TKey key, TValue value)
continue;
}

if (distance >= _maxProbeSequenceLength)
{
Resize();
EmplaceInternal(ref entry);
Count++;
return true;
}

if (_keyComparer.Equals(key, Find(_entries, index).Key))
{
return false;
Expand Down Expand Up @@ -563,8 +571,7 @@ public TValue this[TKey key]
private uint Hash(TKey key)
{
var hashcode = (uint)key.GetHashCode();
var result = _goldenRatio * hashcode;
return result >> _shift;
return (_goldenRatio * hashcode) >> _shift;
}

/// <summary>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ public void Emplace_StealsEntryWhenPslIsGreater()
}

[Fact]
public void Emplace_AddKeysFromEnumeratorToAnotherHashmap()
public void Emplace_AddKeysFromKeysEnumeratorToAnotherHashmap()
{
var robinhoodMap = new RobinhoodMap<uint, uint>(12_000_000);
var rnd0 = new Random(3);
Expand All @@ -75,7 +75,7 @@ public void Emplace_AddKeysFromEnumeratorToAnotherHashmap()

var rndInts = robinhoodMap.Keys.ToArray();

RobinhoodMap<uint, uint> map = new(16);
RobinhoodMap<uint, uint> map = new(64);

for (uint i = 0; i < rndInts.Length; i++)
{
Expand All @@ -84,6 +84,5 @@ public void Emplace_AddKeysFromEnumeratorToAnotherHashmap()
map.Emplace(v, v);
}
}

}
}

0 comments on commit 6e937dc

Please sign in to comment.