This question already has an answer here:
Closed 11 years ago.
Possible Duplicate:
Sorting by Name (alphabetic)
Say I have the code below. I have a total of 6 radio buttons. I have the 5 of the radio buttons working. The last is called radio button is called rbRegion. I believe I have everything set up correctly. There are two arrays, one for strings, and one for 4 quarterly totals and one yearly total. Say I wanted to sort by region name, I would place it in the `if (rbRegion.Checked) area. What exactly would I need to place in there to sort it alphabetically and to change the corresponding numeric array.
private void btnSort_Click(object sender, EventArgs e)
{
int n;
decimal temp;
int sortCol = 0;
string ntemp;
bool swapFlag;
if (rb1.Checked)
sortCol = 0;
if (rb2.Checked)
sortCol = 1;
if (rb3.Checked)
sortCol = 2;
if (rb4.Checked)
sortCol = 3;
if (rbTotal.Checked)
sortCol = 4;
if (rbRegion.Checked)
{
}
else
{
do
{
swapFlag = false;
for (n = 0; n < lastIndexUsed; n++)
{
if(quarters[n,sortCol] < quarters[n+1, sortCol])
{
//column 4
temp = quarters[n, 4];
quarters[n, 4] = quarters[n + 1, 4];
quarters[n+1, 4] = temp;
//col 3
temp = quarters[n, 3];
quarters[n, 3] = quarters[n + 1, 3];
quarters[n + 1, 3] = temp;
//col 2
temp = quarters[n, 2];
quarters[n, 2] = quarters[n + 1, 2];
quarters[n + 1, 2] = temp;
// col 1
temp = quarters[n, 1];
quarters[n, 1] = quarters[n + 1, 1];
quarters[n + 1, 1] = temp;
//col 0
temp = quarters[n, 0];
quarters[n, 0] = quarters[n + 1, 0];
quarters[n + 1, 0] = temp;
//name
ntemp = Branch[n];
Branch[n] = Branch[n + 1];
Branch[n + 1] = ntemp;
swapFlag = true;
}//endif
}//for end
} while (swapFlag);
}
If the value inside the rbRegion.Checked condition is an array. you can use this code.
Array.Sort(YourStringArray); // Ascending
Array.Reverse(YourStringArray); // Descending
Related
I have a 2D Array in C# with user input to fill the Array. I need help to find the sum for every column and row.
var input = Console.ReadLine();
var n = int.Parse(input);
int[,] intArr = new int[n, 3];
for (int i = 0; i < n; i++)
{
input = Console.ReadLine();
var parts = input.Split(' ');
for (int j = 0; j < 3; j++)
{
intArr[i, j] = int.Parse(parts[j]);
}
}
if (n == 1)
{
Console.WriteLine("Sum of column " + Convert.ToString(n) + ": " + (intArr[n - 1, 0] + intArr[n - 1, 1] + intArr[n - 1, 2]));
Console.WriteLine("Row1: " + (intArr[n - 1, 0]));
Console.WriteLine("Row2: " + (intArr[n - 1, 1]));
Console.WriteLine("Row3: " + (intArr[n - 1, 2]));
}
if (n == 2)
{
Console.WriteLine("Sum of column " + Convert.ToString(n - 1) + ": " + (intArr[n - 2, 0] + intArr[n - 2, 1] + intArr[n - 2, 2]));
Console.WriteLine("Sum of column " + Convert.ToString(n) + ": " + (intArr[n - 1, 0] + intArr[n - 1, 1] + intArr[n - 1, 2]));
Console.WriteLine("Row 1: " + (intArr[n - 2, 0] + intArr[n - 1, 0]));
Console.WriteLine("Row 2: " + (intArr[n - 2, 1] + intArr[n - 1, 1]));
Console.WriteLine("Row 3: " + (intArr[n - 1, 2] + intArr[n - 1, 1]));
}
}
User input:
2
1 2 3
4 5 6
The output:
Sum of column 1: 6
Sum of column 2: 15
Row 1: 5
Row 2: 7
Row 3: 11
I want this output for N columns enter by user, but I am stuck!
Thank you!
Not sure, is your problem that you get an undesired result or that you have a model with a fixed number of elements? An array is a fixed size data container, so if you want any number of columns the architecture perhaps is where you want to change away from array.
Anyway, problem 1 is that you let user chose how many rows they want, but now how many column, so presuming there will be 3 conflicts with you data. So you have on array the .getUpperBound() for that which takes a range parameter and this way we can use a dynamic strucure
//From:
for (int i = 0; i < n; i++)
{
input = Console.ReadLine();
var parts = input.Split(' ');
for (int j = 0; j < 3; j++)
{
intArr[i, j] = int.Parse(parts[j]);
}
}
//TO:
var rows = new List<int[]>();
for (int i = 0; i < n; i++)
{
input = Console.ReadLine();
var parts = input.Split(' ');
var listOf = new List<int>();
for (int j = 0; j < parts.GetUpperBound(0); j++)
{
listOf.Add(int.Parse(parts[j]));
}
rows.Add(listOf.ToArray());
}
from https://learn.microsoft.com/en-us/dotnet/api/system.linq.enumerable.aggregate?view=net-5.0 You get the aggregation capability
[Fact]
public void SumExerciseTest()
{
/*
The output:
Sum of column 1: 6
Sum of column 2: 15
Row 1: 5
Row 2: 7
Row 3: 11 => 9
*/
var testData = new[] { "1 2 3", "4 5 6" };
var input = "2"; // Console.ReadLine();
var n = int.Parse(input);
var rows = new List<int[]>(n);
for (int i = 0; i < n; i++)
{
input = testData[i];
var parts = input.Split(' ');
var listOf = new List<int>();
for (int j = 0; j <= parts.GetUpperBound(0); j++)
{
listOf.Add(int.Parse(parts[j]));
}
rows.Add(listOf.ToArray());
}
var rowSums = new List<int>(n);
foreach (int[] row in rows)
{
rowSums.Add(row.Aggregate((result, item) => result + item));
}
int maxLength = 0;
var rowLengths = new List<int>(n);
foreach (int[] row in rows)
{
rowLengths.Add(row.Length);
}
maxLength = rowLengths.Max();
int[] columnSums = new int[maxLength];
for (int idx = 0; idx < columnSums.Length; idx++){
foreach (var row in rows)
{
if (row.GetUpperBound(0) >= idx)
{
columnSums[idx] += row[idx];
}
}
}
int counter = 0;
//Outputting:
foreach(var sum in rowSums)
{
counter += 1;
System.Diagnostics.Debug.WriteLine($"Row {counter}: {sum}");
}
counter = 0;
foreach(var sum in columnSums)
{
counter += 1;
System.Diagnostics.Debug.WriteLine($"Column {counter}: {sum}");
}
Well, let's implement (extract) methods for summing arbitrary column and row:
private static int SumColumn(int[,] array, int column) {
if (array == null)
throw new ArgumentNullException(nameof(array));
if (column < 0 || column >= array.GetLength(1))
throw new ArgumentOutOfRangeException(nameof(column));
int result = 0;
for (int r = 0; r < array.GetLength(0); ++r)
result += array[r, column];
return result;
}
private static int SumRow(int[,] array, int row) {
if (array == null)
throw new ArgumentNullException(nameof(array));
if (row < 0 || row >= array.GetLength(0))
throw new ArgumentOutOfRangeException(nameof(row));
int result = 0;
for (int c = 0; c < array.GetLength(1); ++c)
result += array[row, c];
return result;
}
then you can put
for (int c = 0; c < intArr.GetLength(1); ++c)
Console.WriteLine($" Sum of column {c + 1}: {SumColumn(intArr, c)}");
for (int r = 0; r < intArr.GetLength(0); ++r)
Console.WriteLine($" Sum of row {r + 1}: {SumRow(intArr, r)}");
I am having a bit of trouble with my program which holds student names and grades in a 2D string array. Basically, I have a second (1D) array that will hold average grade for each student.
code so far:
class Program
{
static void Main(string[] args)
{
// Create a 2D array for names, and their grades, and an array for average grades
string[,] studentGrades = new string[5, 8];
int[] average = new int[studentGrades.GetLength(0)];
// Set student names/grades manually
studentGrades[0, 0] = "Steve";
studentGrades[0, 1] = "69";
studentGrades[0, 2] = "80";
studentGrades[0, 3] = "66";
studentGrades[0, 4] = "75";
studentGrades[0, 5] = "90";
studentGrades[0, 6] = "69";
studentGrades[0, 7] = "98";
studentGrades[1, 0] = "Bob";
studentGrades[1, 1] = "73";
studentGrades[1, 2] = "67";
studentGrades[1, 3] = "65";
studentGrades[1, 4] = "91";
studentGrades[1, 5] = "48";
studentGrades[1, 6] = "33";
studentGrades[1, 7] = "94";
studentGrades[2, 0] = "Lewis";
studentGrades[2, 1] = "67";
studentGrades[2, 2] = "80";
studentGrades[2, 3] = "66";
studentGrades[2, 4] = "75";
studentGrades[2, 5] = "90";
studentGrades[2, 6] = "69";
studentGrades[2, 7] = "63";
studentGrades[3, 0] = "Sara";
studentGrades[3, 1] = "55";
studentGrades[3, 2] = "58";
studentGrades[3, 3] = "63";
studentGrades[3, 4] = "70";
studentGrades[3, 5] = "55";
studentGrades[3, 6] = "55";
studentGrades[3, 7] = "76";
studentGrades[4, 0] = "Xavier";
studentGrades[4, 1] = "22";
studentGrades[4, 2] = "27";
studentGrades[4, 3] = "25";
studentGrades[4, 4] = "19";
studentGrades[4, 5] = "42";
studentGrades[4, 6] = "18";
studentGrades[4, 7] = "32";
// Loop the array dimensions and output/format output the names/grades
for (int name = 0; name < studentGrades.GetLength(0); name++)
{
for (int grade = 0; grade < studentGrades.GetLength(1); grade++)
{
Console.WriteLine(studentGrades[name, grade]);
}
Console.WriteLine("");
}
for (int i = 0; i < studentGrades.GetLength(0); i++)
{
for (int j = 0; j < studentGrades.GetLength(1); j++)
{
average[j] += int.Parse(studentGrades[i, j]);
}
}
}
}
I get an un-handled exception in regards to the input string not being in the correct format where the average is set.
All help is appreciated!
Update
I've reviewed the solutions of code so far below, and I'm still having issues with getting the grade average to work as intended. I have 5 students with 7 grades. I want the program to output the average of each persons grades below their column.
Code:
static void Main(string[] args)
{
// Create a 2D array for names, and their grades, and an array for average grades
string[,] studentGrades = new string[5, 8];
int[] average = new int[studentGrades.GetLength(1)];
// Set student names/grades manually
//As done above, excluded for brevity reasons
// Loop the array dimensions and output/format output the names/grades
for (int grade = 0; grade < studentGrades.GetLength(1); grade++)
{
for (int name = 0; name < studentGrades.GetLength(0); name++)
{
// Composite formatting is used to align names/grades in grid -- specifically the alignment component.
// Making the value higher (more neg) will increase spacing between elements
// Positive number would right align elements instead
Console.Write("{0, -15}", studentGrades[name, grade]);
}
// Moves each printed grade to a new line
Console.WriteLine("");
}
for (int i = 0; i < studentGrades.GetLength(0); i++)
{
for (int j = 1; j < studentGrades.GetLength(1); j++)
{
average[j] += int.Parse(studentGrades[i, j]);
}
average[i] /= studentGrades.GetLength(1) - 1;
}
for (int i = 0; i <= average.GetLength(0) - 1; i++)
{
Console.Write("{0, -15}", i);
}
Console.WriteLine("");
}
Update 2
It seems that the average array is not being properly populated. It seems to just print out 1, 2, 3, 4, 5, 6, 7 if I remove the average division. Furthermore, if I change averages' length to 5 -- or the length of the amount of names since there will only be 5 values, it breaks. This is likely because it's trying to add 7 items to a 5 item array.
Every studentGrages[*, 0] element is not integer so you can't parse it to int
Skip the first elements
for (int i = 0; i < studentGrades.GetLength(0); i++)
{
for (int j = 1; j < studentGrades.GetLength(1); j++)
{
average[j] += int.Parse(studentGrades[i, j]);
}
}
You have to change this part of code:
// Store the average as a double array, otherwise you can't have averages with decimal values.
double[] average = new double[studentGrades.GetLength(0)];
for (int i = 0; i < studentGrades.GetLength(0); i++)
{
// Start from j = 1, as j = 0 would get a name instead of a grade.
for (int j = 1; j < studentGrades.GetLength(1); j++)
{
// Here use average[i] instead of average[j], because you want
// the average grade for each student.
average[i] += int.Parse(studentGrades[i, j]);
}
// Finish calculating the average.
// GetLength(0) - 1 because the first item is a name, not a grade.
average[i] /= studentGrades.GetLength(1) - 1;
}
for (int i = 0; i <= average.GetLength(0) - 1; i++)
{
// Show at most 2 decimal digits.
Console.Write("{0, -15:#.##}", average[i]);
}
Your trying to include the string of the names (on the 0 index) with the average. e.g int.Parse("Steve") which is causing the exception, just skip on the first element on each colum.
for (int j = 1; j < studentGrades.GetLength(1); j++)
As other have rightly pointed out, you need to change the 0 to a 1 in the following line:
for (int j = 1; j < studentGrades.GetLength(1); j++)
Otherwise you're going to try to parse the name as an integer.
Also you need to change the index on average inside the loop to i rather than j.
average[i] += int.Parse(studentGrades[i, j]);
The other issue that you're going to have is that you're using integer mathematics - so when you do something like 7 / 2 you get an answer of 3 and not 3.5.
If I were you, and you don't want to change your data structure, I would do it this way:
var results =
studentGrades
.Cast<string>()
.Select((x, n) => new { x, n })
.GroupBy(xn => xn.n / studentGrades.GetLength(1), xn => xn.x)
.Select(xs => new
{
student = xs.First(),
average = xs.Skip(1).Select(x => int.Parse(x)).Average(),
})
.ToArray();
That gives me:
Alternatively, I would suggest that you change your data structure to this:
var studentGrades = new []
{
new { student = "Steve", grades = new [] { 69, 80, 66, 75, 90, 69, 98, } },
new { student = "Bob", grades = new [] { 73, 67, 65, 91, 48, 33, 94, } },
new { student = "Lewis", grades = new [] { 67, 80, 66, 75, 90, 69, 63, } },
new { student = "Sara", grades = new [] { 55, 58, 63, 70, 55, 55, 76, } },
new { student = "Xavier", grades = new [] { 22, 27, 25, 19, 42, 18, 32, } },
};
Then this should work for you:
var results =
studentGrades
.Select(sg => new
{
sg.student,
average = sg.grades.Average(),
})
.ToArray();
Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 8 years ago.
Improve this question
I am trying to perform a bubble sort on a 2D array, sorting by the third index (the integer)
string[,] edges = new string[,] { {"A", "B", "2"},
{"A", "C", "3"},
{"A", "E", "10"},
{"B", "C", "5"},
{"B", "D", "10"},
{"C", "D", "2"},
{"D", "E", "5"},
{"E", "B", "3"}
};
I get an IndexOutOfRangeException on IF statenent of the sort code
string[] temp = {};
//sort edges and add them to sortedEdges - using bubblesort
for (int i = 0; i < edges.Length - 1; i++){
for (int j = 0; j < edges.Length - 1; j++){
if (Int32.Parse(edges[i, 2]) > Int32.Parse(edges[i + 1, 2])){
//make a swap
//put array record i into temp holder
temp[0] = edges[i, 0];
temp[1] = edges[i, 1];
temp[2] = edges[i, 2];
//copy i + 1 into i
edges[i, 0] = edges[i + 1, 0];
edges[i, 1] = edges[i + 1, 1];
edges[i, 2] = edges[i + 1, 2];
//copy temp into i + 1
edges[i + 1, 0] = temp[0];
edges[i + 1, 1] = temp[1];
edges[i + 1, 2] = temp[2];
}
}
}
My question is, how do I fix this so that the array "edges" is filled with the rows, ordered by the third column?
Thanks.
UPDATED v-3
The problem was in Length for such defined table which in your case was 24 because it seems to count all the elements in both dimensions.
Please try the following code:
string[] temp = new string[3];
for (int i = 0; i < edges.GetLength(0) - 1; i++){
int j;
j = 0;
for (; j < edges.GetLength(0) - 1; j++){
if (Int32.Parse(edges[j, 2]) > Int32.Parse(edges[j + 1, 2])){
//make a swap
//put array record j into temp holder
temp[0] = edges[j, 0];
temp[1] = edges[j, 1];
temp[2] = edges[j, 2];
//copy j + 1 into j
edges[j, 0] = edges[j + 1, 0];
edges[j, 1] = edges[j + 1, 1];
edges[j, 2] = edges[j + 1, 2];
//copy temp into j + 1
edges[j + 1, 0] = temp[0];
edges[j + 1, 1] = temp[1];
edges[j + 1, 2] = temp[2];
}
}
}
You can find (updated) working example here: https://dotnetfiddle.net/FQs4OA
I have a matrix of 50 rows and 2 columns and I want to sort them based on the comparison of the value of the second column filed. Here what I mean, if my matrix as:
[00][01]
[10][11]
[20][21]
[30][31]
[40][41]
[50][51]
I want to compare [01] and [11] and if [01] lesser than [11] I want to exchange the entire second row with the first row, to be like this (for example):
[10][11]
[00][01]
[20][21]
[30][31]
[40][41]
[50][51]
I tried using C# and came up with this algorithm but it didn't work:
int temp1, temp2;
for (int i = 0; i < 50; i++)
{
for (int j = i + 1; j < 2; j++)
{
if (rating[i, j] < rating[i + 1, j])
{
temp1 = rating[i + 1, j - 1];
temp2 = rating[i + 1, j];
rating[i + 1, j - 1] = rating[i, j - 1];
rating[i + 1, j] = rating[i, j];
rating[i, j - 1] = temp1;
rating[i, j] = temp2;
}
}
}
Can someone tell me a key to workout this problem or if you have the answer in c,c++ or another language please share it with us.
Thank you.
I believe you are trying to sort the matrix in descending order of second column. Give this code a try.
int[][] mat = new[] { new[] { 4, 4 }, new[] { 5, 1 }, new[] { 3, 2 }, new[] { 6, 1 } };
var ordered = mat.OrderByDescending(i => i[1]);
Your implementation of sort algorithm is wrong. The inner loop should not run from i+1 to 1.
Try implementing the simple bubble sort:
for (int i = 0; i < 50; i++)
{
for (int j = 0; j < 49-i; j++)
{
if (rating[j, 1] < rating[j + 1, 1]) // column 1 entry comparison
{
temp1 = rating[j, 0]; // swap both column 0 and column 1
temp2 = rating[j, 1];
rating[j, 0] = rating[j+1, 0];
rating[j, 1] = rating[j+1, 1];
rating[j+1, 0] = temp1;
rating[j+1, 1] = temp2;
}
}
}
I've initialized a 2 dimensional array and starting from index 5 onwards contain null value. I'm trying to add the array values to my Chart Control. When I try displaying the values to Console.WriteLine, there's no exception occurred however when I add to my chart series, the exception is "Index was outside the bounds of the array." Anyone can help me? is it because chart control has limited bars?
try
{
//females age range
string[,] gAge = new string[10, 2];
gAge[0, 0] = "F.13-17";
gAge[0, 1] = yf.f1317.ToString();
gAge[1, 0] = "F.18-24";
gAge[1, 1] = yf.f1824.ToString();
gAge[2, 0] = "M.25-34";
gAge[2, 1] = yf.m2534.ToString();
gAge[3, 0] = "M.13-17";
gAge[3, 1] = yf.m1317.ToString();
gAge[4, 0] = "M.18-24";
gAge[4, 1] = yf.m1824.ToString();
for (int i = 0; i < gAge.Length; i++)
{
if (gAge[i, 0] == null)
{
break;
}
else
{
Console.WriteLine(gAge[i, 0].ToString());
string[] seriesArray = { gAge[i, 0].ToString() };
Series series = this.chart1.Series.Add(seriesArray[i]);
}
}
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
The problem is that you are getting the length of your entire array, in this casegAge.Length is equal to 20 which is the total number of indices in your Array. It is exceeding the bounds of your first array dimension. Try using gAge.GetLength(0) instead.
try
{
chart1.Series.Clear();
chart1.Titles.Clear();
chart1.Visible = true;
//CODES HERE TO GET THE SELECTED PAGE FROM DROP DOWN LIST
var fb = new FacebookClient(myToken.Default.token);
var query = string.Format("SELECT metric, value FROM insights WHERE object_id=132414626916208 AND metric='page_fans_gender_age' AND period = period('lifetime') AND end_time = end_time_date('2013-01-18')");
dynamic parameters = new ExpandoObject();
parameters.q = query;
var data = fb.Get<genderAgeDataII>("fql", parameters);
genderAge yf = (genderAge)data.data[0].value;
//females age range
string[,] gAge = new string[10, 2];
gAge[0, 0] = "F.13-17";
gAge[0, 1] = yf.f1317.ToString();
gAge[1, 0] = "F.18-24";
gAge[1, 1] = yf.f1824.ToString();
gAge[2, 0] = "M.25-34";
gAge[2, 1] = yf.m2534.ToString();
gAge[3, 0] = "M.13-17";
gAge[3, 1] = yf.m1317.ToString();
gAge[4, 0] = "M.18-24";
gAge[4, 1] = yf.m1824.ToString();
for (int i = 0; i < gAge.GetLength(0); i++)
{
if (gAge[i, 0] == null)
{
break;
}
else
{
string[] seriesArray = { gAge[i,0] };
// Add series.
for (int w = 0; w < seriesArray.Length; w++)
{
// Add series.
Series series = this.chart1.Series.Add(seriesArray[w]);
int[] pointsArray = new int[seriesArray.Length];
pointsArray[w] = Convert.ToInt32(gAge[i, 1]);
series.Points.Add(pointsArray[w]);
}
Console.WriteLine(gAge[i, 0].ToString());
}
}