2

I would like to accomplish what the title states but I don't know how to go about doing so.

I have 2 lists:

public List<int[,]> LongList = new List<int[,]>();
public List<int[,]> UniqueList = new List<int[,]>();

To further explain, here's a scenario:

Puzzles:

public int[,] puzzle1 = new int [3,3] { {1,2,3},
                                            {8,4,0},
                                            {7,6,5} }; //[1,2,3;8,4,0;7,6,5]

    public int[,] puzzle2 = new int [3,3] { {8,7,6},
                                            {1,0,5},
                                            {2,3,4}  }; //[8,7,6;1,0,5;2,3,4]


    public int[,] puzzle3 = new int [3,3] { {7,6,3},
                                            {1,0,2},  
                                            {8,4,5}  }; //[7,6,3;1,0,2;8,4,5]

LongList contains:

LongList.Add(puzzle1); 
LongList.Add(puzzle1); 
LongList.Add(puzzle1); 
LongList.Add(puzzle1);
LongList.Add(puzzle2);
LongList.Add(puzzle2);
LongList.Add(puzzle3);
LongList.Add(puzzle3);
LongList.Add(puzzle3);

I would like Unique list to hold the UNIQUE values from LongList. AS IF this happened:

UniqueList.Add(puzzle1);
UniqueList.Add(puzzle2);
UniqueList.Add(puzzle3);

As an equation: UniqueList = Distinct values from LongList

List is full of multiple reoccurring values & I would like to take only the unique ones and put them into UniqueList.

I'm trying to complete a puzzle and the LongList will contain multiple references of the same same puzzle and more. To make it simple for case of discussion:

LongList values: 1,1,1,1,2,2,3,4,4,4,4,5,5

I would like UniqueList to contain the puzzles: 1,2,3,4,5

Glitchezz
  • 353
  • 2
  • 7
  • 21

2 Answers2

2

OP's comments are vague.

Option 1: Unique numbers from across all multidimensional arrays

List<int> UniqueList = new List<int>();

UniqueList = LongList.Select(i => Flatten(i))
               .SelectMany(i => i)
               .Distinct()
               .ToList();

This would turn { [[0, 1], [2, 3]], [[2, 2], [4, 5]] } to { 0, 1, 2, 3, 4, 5 }

See below for Flatten

Option 2: Unique multidimensional arrays by values

NB: Assumes size and number of dimensions of each multidimensional array match.

List<int[,]> UniqueList = new List<int[,]>();
foreach (var e in LongList)
{
  IEnumerable<int> flat = Flatten(e);
  if (!UniqueList.Any(i => Flatten(i).SequenceEqual(flat)))
  {
    UniqueList.Add(e);
  }
}

This would turn { [[0, 1], [2, 3]], [[0, 1], [2, 3]], [[2, 2], [4, 5]] } to { [[0, 1], [2, 3]], [[2, 2], [4, 5]] }

See below for Flatten

Option 3: Unique references only

UniqueList = aList.Distinct().ToList();

NB: This was the original answer, for context on the comments.

Flatten Method

In all cases Flatten is taken from Guffa's SO Answer

public static IEnumerable<T> Flatten<T>(T[,] items) {
  for (int i = 0; i < items.GetLength(0); i++)
    for (int j = 0; j < items.GetLength(1); j++)
      yield return items[i, j];
}

Other options

If OP would like something else (e.g. flattenting List<int[,]> to List<int[]> or support for different sized multidimensional arrays) they will have to comment back.

Community
  • 1
  • 1
Matt Mitchell
  • 40,943
  • 35
  • 118
  • 185
  • Depends on your definition of 'unique'. I ran a test in LINQPad and it matched my intuition. I'll grab the code and post back. – Matt Mitchell Apr 04 '13 at 02:24
  • 1
    I just checked and it doesn't. – Julián Urbano Apr 04 '13 at 02:26
  • By unique I mean: List would contain values: 1,1,1,2,2,2,2,3,3,4,4,4,4,5 (made simple for explanation as they're actually multi dimensional results). And I only want UniqueList to hold: 1,2,3,4,5 – Glitchezz Apr 04 '13 at 02:26
  • Yeah it performs reference equality, not same value equality. Okay deleting my answer as it's incorrect for what the OP wants. – Matt Mitchell Apr 04 '13 at 02:28
  • I don't think your explanation is simplifying. It actually complicates it. Can you give a multi-D example of what you're after? It sounds like only the unique numbers across all multi-dimensional arrays? Or a set of multi-dimensional arrays that only contain the unique numbers in each corresponding source array? – Matt Mitchell Apr 04 '13 at 02:44
  • Im sorry, please have a look at my edited question. If you need more info please let me know! – Glitchezz Apr 04 '13 at 03:00
2

Based on OP's update, we just need to remove duplicate references. So we do not need to compare on a per-value basis. Distinct should do:

UniqueList = LongList.Distinct().ToList();
Julián Urbano
  • 8,378
  • 1
  • 30
  • 52
  • haha my first answer... I'm upvoting you anyway for being as patient with this as I was :-) – Matt Mitchell Apr 04 '13 at 03:23
  • 1
    I was just thinking about it...update yours and let that be the answer :-) btw...I'm not sure if it's really just references or he just made that example to keep it simple... – Julián Urbano Apr 04 '13 at 03:25
  • Based on his comment that it "contains multiple references of the same puzzle" you sound like you've interpreted it right to me. – Matt Mitchell Apr 04 '13 at 03:44
  • not sure, really. +1 to you too and let him decide what he means :-) – Julián Urbano Apr 04 '13 at 03:49
  • Thanks a lot guys! If I were to call upon the unique list like so: UniqueList[0] UniqueList[1] UniqueList[2] I would need that to grab puzzle1, puzzle2 & puzzle 3 (with NO duplicates that the LongList holds).. Does this code provide that? – Glitchezz Apr 04 '13 at 15:31