fork(1) download
  1. #include <errno.h>
  2. #include <stdio.h>
  3. #include <stdlib.h>
  4. #include <string.h>
  5.  
  6. /* qsort C-string comparison function from qsort(3) man-page */
  7. static int
  8. cmpstringp(const void *p1, const void *p2)
  9. {
  10. /* The actual arguments to this function are "pointers to
  11.   pointers to char", but strcmp(3) arguments are "pointers
  12.   to char", hence the following cast plus dereference */
  13.  
  14. return strcmp(* (char * const *) p1, * (char * const *) p2);
  15. }
  16.  
  17. static double
  18. get_score(int scores) {
  19. size_t sum = 0, nscores = 0;
  20. for ( ; scores > 0; scores /= 10) {
  21. sum += scores % 10;
  22. ++nscores;
  23. }
  24. return (double)sum / nscores; /*XXX remove /nscore to get mere sum */
  25. }
  26.  
  27. int main(void) {
  28. const char* student_list[] = {
  29. /* группа | фио | оценки */
  30. "4272 Галкин Г. А. 5445",
  31. "4273 Константинопольский А. А. 4333",
  32. "4273 Курочкин А. А. 3433",
  33. "4272 Козлов И. И. 4443"
  34. };
  35. const size_t n = sizeof(student_list) / sizeof(student_list[0]);
  36. const char* *pstudent = NULL;
  37. int last_group = -1;
  38. double group_score = 0;
  39. size_t group_count = 0;
  40.  
  41. qsort(student_list, n, sizeof(student_list[0]), cmpstringp);
  42.  
  43. for (pstudent = student_list; pstudent != &student_list[n]; ++pstudent) {
  44. int group = -1, scores = -1;
  45. char *name = NULL;
  46.  
  47. errno = 0;
  48. if (sscanf(*pstudent, "%d %m[^0-9] %d", &group, &name, &scores) != 3) {
  49. if (errno) perror("sscanf");
  50. fprintf(stderr, "error: can't parse '%s'\n", *pstudent);
  51. exit(EXIT_FAILURE);
  52. }
  53. if (group != last_group) {
  54. if (group_count > 0) /* print the last group average score */
  55. printf("%d %f\n", last_group, (double)group_score/group_count);
  56.  
  57. group_score = 0; /* start new group */
  58. group_count = 0;
  59. last_group = group;
  60. }
  61. ++group_count;
  62. group_score += get_score(scores);
  63. free(name);
  64. }
  65. if (group_count > 0) /* print the last group average score */
  66. printf("%d %f\n", last_group, (double)group_score/group_count);
  67. return 0;
  68. }
  69.  
Success #stdin #stdout 0s 2380KB
stdin
Standard input is empty
stdout
4272 4.125000
4273 3.250000