Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Two-Way Mapping list

Tags:

c#

mapping

I need to save 2 values in one list so I have all the positions AND my controls of my board in one list. I was using a Dictionary but I found out that there is only one way mapping. Does anyone have any recommendations except a 2-dimensional Array?

like image 433
Tom Kerkhove Avatar asked Nov 12 '11 14:11

Tom Kerkhove


2 Answers

This may help:

 public class BiDirectionalDictionary<L, R>
{
    private readonly Dictionary<L, R> leftToRight = new Dictionary<L, R>();
    private readonly Dictionary<R, L> rightToLeft = new Dictionary<R, L>();
    public void Add(L leftSide, R rightSide)
    {
        if (leftToRight.ContainsKey(leftSide) ||
            rightToLeft.ContainsKey(rightSide))
            throw new DuplicateNameException();
        leftToRight.Add(leftSide, rightSide);
        rightToLeft.Add(rightSide, leftSide);
    }
    public L this[R rightSideKey]
    { get { return rightToLeft[rightSideKey]; } }
    public R this[L leftSideKey]
    { get { return leftToRight[leftSideKey]; } }
    public bool ContainsKey(L leftSideKey)
    { return leftToRight.ContainsKey(leftSideKey); }
    public bool ContainsKey(R rightSideKey)
    { return rightToLeft.ContainsKey(rightSideKey); }
}
 [Serializable]
public class DuplicateNameException : SystemException
{
    protected DuplicateNameException(
           SerializationInfo info, StreamingContext context);
    public DuplicateNameException();
    public DuplicateNameException(string s);
    public DuplicateNameException(string message, 
           Exception innerException);
}

This has an issue if the left side and right side are the same type... i.e., it doesn't work right if you try

var myBiDireDict = new BiDirectionalDictionary<DateTime, DateTime>();
like image 124
Charles Bretana Avatar answered Nov 02 '22 23:11

Charles Bretana


You can use a dictionary easily enough as a two-way mapping if you don't care about linear search performance for the reverse mapping (which you'd get with a 2D array anyway):

var dictionary = new Dictionary<string, int>();
// Fill it up...
int forwardMapResult = dictionary["SomeKey"];
string reverseMapResult = dictionary.Where(kvp => kvp.Value == 5).First().Key;

If the lookup speed is an issue than you'll have to maintain two dictionaries - one for the forward lookup and one for the reverse. Or use an in-memory, indexable database such as SQLite.

like image 44
Aaronaught Avatar answered Nov 02 '22 23:11

Aaronaught