There's an input:
8 4 6 6 6 6 6 6
7 5 7 6 6 6 6 5
6 6 6 5 5 5 5 6
8 6 8 7 7 7 7 6
8 6 6 6 6 6 6 6
8 6 6 6 6 6 6 1
I have to find the greatest numbers in each column and get their row index, if there's multiple of the same greatest number in one column, I have to get all of their row indexes, and put them in an array, but if there's multiple of the same row index I just need one, and I have to put them in ascending order.
The first column's greatest number is 8, so the indexes from the first column are 0, 3, 4, 5. The second colum's greatest number is 6, so the indexes from the second column are 2, 3, 4, 5 but I already have 3, 4, and 5 so I just need the 2 In the end I should have 0, 2, 3, 4, 5.
while (p < M) //Getting the greatest numbers of each column
{
for (int l = 0; l < N; l )
{
if (matrix[l, p] > max)
{
max = matrix[l, p];
}
}
greatestNum[p] = max;
max = 0;
p ;
}
I just need help with getting the indexes and with the no duplicates thing. I can do the ascending order by myself. Every help is appreciated.
CodePudding user response:
You can use HashSet<T> to store unique values of indexes.
GreatestNumberIndexes method finds maximums of current column and then adds the indexes of result HashSet. You can do ToArray() to get the indexes as an array too.
Here's the code:
private static HashSet<int> GreatestNumberIndexes(int[,] matrix,
int rows, int cols)
{
var indexes = new HashSet<int>();
for (var i = 0; i < cols; i )
{
var max = int.MinValue;
for (int j = 0; j < rows; j )
if (matrix[j, i] > max)
max = matrix[j, i];
for (int j = 0; j < rows; j )
if (matrix[j, i] == max)
indexes.Add(j);
}
return indexes;
}
CodePudding user response:
You can use HashSet<int> to store unique rows:
using System.Linq;
...
private static int[] myIndexes(int[,] data) {
// distinct rows which contain max values
HashSet<int> result = new HashSet<int>();
// for each column we find rows that contain max values
for (int c = 0; c < data.GetLength(1); c) {
// max value so far
int max = data[0, c];
// List - we can have several rows with max value
List<int> maxRows = new List<int>() {1};
for (int r = 1; r < data.GetLength(0); r)
if (data[r, c] == max)
maxRows.Add(r 1);
else if (data[r, c] > max) {
maxRows.Clear();
max = data[r, c];
maxRows.Add(r 1);
}
foreach (int item in maxRows)
result.Add(item);
}
// let's return ordered rows - OrderBy
return result
.OrderBy(row => row)
.ToArray();
}
CodePudding user response:
Not the most elegant solution but:
int[,] matrix = new int[,]
{
{8, 4, 6, 6, 6, 6, 6, 6},
{7, 5, 7, 6, 6, 6, 6, 5},
{6, 6, 6, 5, 5, 5, 5, 6},
{8, 6, 8, 7, 7, 7, 7, 6},
{8, 6, 6, 6, 6, 6, 6, 6},
{8, 6, 6, 6, 6, 6, 6, 1}
};
HashSet<int> indicesOfMaxNumbers = new HashSet<int>();
for (int col = 0; col < matrix.GetLength(1); col )
{
int curMax = matrix[0, col];
for (int row = 1; row < matrix.GetLength(0); row )
{
if (curMax <= matrix[row, col])
{
curMax = matrix[row, col];
}
}
for (int row = 0; row < matrix.GetLength(0); row )
{
if (curMax == matrix[row, col])
{
indicesOfMaxNumbers.Add(row 1);
}
}
}
indicesOfMaxNumbers.Sort();
Console.WriteLine(string.Join(", ", indicesOfMaxNumbers));
I find the greatest element in each column and then I insert the index if it is not already been inserted.
P.S. you can play with it a bit to optimize it as I am 100% sure there is a better solution
CodePudding user response:
// init your example of rows
var matrixXY = new List<List<int>>
{
new List<int>{8, 4, 6, 6, 6, 6, 6, 6},
new List<int>{7, 5, 7, 6, 6, 6, 6, 5},
new List<int>{6, 6, 6, 5, 5, 5, 5, 6},
new List<int>{8, 6, 8, 7, 7, 7, 7, 6},
new List<int>{8, 6, 6, 6, 6, 6, 6, 6},
new List<int>{8, 6, 6, 6, 6, 6, 6, 1}
};
// turn it around for easier management
var matrixYX = new List<List<int>>();
for (int y = 0; y < matrixXY[0].Count; y )
{
matrixYX.Add(new List<int>());
for (int x = 0; x < matrixXY.Count; x )
{
matrixYX[y].Add(matrixXY[x][y]);
}
}
// get index of each max number per column
var indexGroups = matrixYX.Select(values =>
{
var maxValue = values.Max();
return values
.Select((value, i) => (Value: value, Index: i 1))
.Where(tuple => tuple.Value == maxValue)
.Select(tuple => tuple.Index);
});
// pass all indexes into one array
var result = indexGroups
.SelectMany(indexes => indexes)
.Distinct();
