0

Hi!
I have a problem to make a list of students (i know how to put all the input and to calculate the average of the students grades) but i don't know how to put the students in new list arrayed by their average form biggest to smallest and if two students have same average grade then they should array by other input data.Please help me!

2
Contributors
1
Reply
2
Views
8 Years
Discussion Span
Last Post by Narue
0

What you want is a multi-key search. If the grades match, compare another key. One way is to do it directly. That way you have more control over ascending and descending. For example if you want to sort the grade descending, but the other key (like a name) ascending:

#include <algorithm>
#include <iostream>
#include <string>

struct Student {
  std::string name;
  int avg_grade;
};

bool multikey_compare ( const Student& a, const Student& b )
{
  if ( a.avg_grade == b.avg_grade )
    return a.name < b.name;

  return a.avg_grade > b.avg_grade;
}

int main()
{
  Student list[] = {
    {"Joe Blow", 80},
    {"Jane Doe", 80},
    {"Fonzie", 60},
    {"The Dude", 70},
    {"Some Guy", 80},
    {"Z Man", 90},
    {"John Doe", 90},
    {"A Man", 70}
  };

  std::sort ( list, list + 8, multikey_compare );

  for ( int i = 0; i < 8; i++ )
    std::cout<< list[i].avg_grade <<'\t'<< list[i].name <<'\n';
}

If both keys are to be sorted the same way, you can concatenate them into a string and then compare the string:

#include <algorithm>
#include <iostream>
#include <sstream>
#include <string>

struct Student {
  std::string name;
  int avg_grade;
};

bool multikey_compare ( const Student& a, const Student& b )
{
  std::ostringstream aout;
  std::ostringstream bout;

  aout<< a.avg_grade << a.name;
  bout<< b.avg_grade << b.name;

  return aout.str() > bout.str();
}

int main()
{
  Student list[] = {
    {"Joe Blow", 80},
    {"Jane Doe", 80},
    {"Fonzie", 60},
    {"The Dude", 70},
    {"Some Guy", 80},
    {"Z Man", 90},
    {"John Doe", 90},
    {"A Man", 70}
  };

  std::sort ( list, list + 8, multikey_compare );

  for ( int i = 0; i < 8; i++ )
    std::cout<< list[i].avg_grade <<'\t'<< list[i].name <<'\n';
}
This question has already been answered. Start a new discussion instead.
Have something to contribute to this discussion? Please be thoughtful, detailed and courteous, and be sure to adhere to our posting rules.