Форум программистов, компьютерный форум CyberForum.ru

С++ для начинающих

Войти
Регистрация
Восстановить пароль
 
 
Exzotick
0 / 0 / 0
Регистрация: 25.05.2014
Сообщений: 25
#1

Возврат функцией массива структур - C++

27.05.2014, 17:39. Просмотров 747. Ответов 23
Метки нет (Все метки)

Пишу программу, которая в зависимости от выбора пользователя считывает информацию о студентах, вводимую с клавиатуры, либо использует заранее подготовленный массив. После этого сортирует массив и выводит таблицу в виде упорядоченного по группам и алфавиту списка. Проблема с использованием массива-заготовки. Как правильно передать его в функцию? И еще вопрос: вот у меня есть структура students, у нее поля name, group и др. Можно ли получить размер определенного поля структуры, не используя непосредственно переменных с этим структурным типом (т.е., я знаю, что, если student1 - переменная структурного типа students, можно написать "sizeof (student1.name)", а можно ли еще как-то)?
Кликните здесь для просмотра всего текста
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
//7.4
#include <iostream>
#include <algorithm>
#include <windows.h>
#include <cstring>
#include <iomanip>
//#include <cstdio>
using namespace std;
 
const int name_size = 30, n = 6;
struct students
{
    char name[name_size];
    char group[n];
    int age;
    float average;
    float scholarship;
};
 
students* fill_arr(int);
students* use_arr();
students  fill_name(students);
students  fill_group(students);
int fill_age(students);
float fill_average(students);
float fill_scholaship(students);
void print_data(students);
void print_data_tab(students);
 
int main()
{
    SetConsoleCP(1251);
    SetConsoleOutputCP(1251);
    char choice;
    students *students_arr = NULL;
    int students_num;
    cout << "Заполните информацию о студентах \n1-ввести данные с клавиатуры \n2-использовать заготовку" << endl;
    cin >> choice;
    switch (choice)
    {
    case '1':
        cout << "Введите количество студентов: ";
        cin >> students_num;
        students_arr = fill_arr(students_num);
        break;
    case '2':
        students_arr = use_arr();
        students_num = sizeof (students_arr) / sizeof (students);
        break;
    }
    system("cls");
    cout << "\nИнформация о студентах: \n" << endl;
    int i, j; students temp;
    for (i = 0; i < students_num; i++)
        for (j = 0; j<students_num - i - 1; j++)
            if (strcmp(students_arr[j].group, students_arr[j + 1].group) > 0)
                swap(students_arr[j], students_arr[j + 1]);
            else
            if (strcmp(students_arr[j].group, students_arr[j + 1].group) == 0)
                if (strcmp(students_arr[j].name, students_arr[j + 1].name) > 0)
                    swap(students_arr[j], students_arr[j + 1]);
    for (int i = 0; i < students_num; i++)
        print_data_tab(students_arr[i]);
    system("pause");
}
students* fill_arr(int students_num)
{
    students* students_arr = new students[students_num];
    for (int i = 0; i < students_num; i++)
    {
        students_arr[i] = fill_name(students_arr[i]);
        students_arr[i] = fill_group(students_arr[i]);
        students_arr[i].age = fill_age(students_arr[i]);
        students_arr[i].average = fill_average(students_arr[i]);
        students_arr[i].scholarship = fill_scholaship(students_arr[i]);
    }
    return students_arr;
}
students* use_arr()
{
    students student1 = { "Урманов Роман Сергеевич", "Б8120", 18, 5.0, 7500 },
        student2 = { "Спицын Вячеслав Валерьевич", "Б8120", 17, 4.5, 0 },
        student3 = { "Аристова Дарья Павловна", "Б8120", 18, 4.0, 0 },
        student4 = { "Иванов Петр Владимирович", "М6180", 22, 5.0, 9000 },
        student5 = { "Дорошин Сергей Александрович", "М6180", 22, 4.9, 2800 },
        student6 = { "Годенко Николай Борисович", "Б5216", 19, 4.3, 2400 },
        student7 = { "Афанасьев Виктор Иванович", "Б5216", 19, 4.0, 1900 },
        student8 = { "Галинов Вячеслав Иванович", "Б5216", 19, 3.8, 0 };
    students default_students_arr[] = { student1, student2, student3, student4, student5, student6, student7, student8 };
    return default_students_arr;
}
students  fill_name(students stu_data)
{
    cout << "\nВведите имя студента: ";
    cin.get();
    gets_s(stu_data.name, sizeof (stu_data.name));
    return stu_data;
}
students fill_group(students stu_data)
{
    cout << "Введите группу: ";
    gets_s(stu_data.group, sizeof (stu_data.group));
    return stu_data;
}
int fill_age(students stu_data)
{
    cout << "Введите возраст студента: ";
    cin >> stu_data.age;
    return stu_data.age;
}
float fill_average(students stu_data)
{
    cout << "Введите средний балл студента: ";
    cin >> stu_data.average;
    return stu_data.average;
}
float fill_scholaship(students stu_data)
{
    cout << "Введите размер стипендии: ";
    cin >> stu_data.scholarship;
    return stu_data.scholarship;
}
void print_data(students stu_data)
{
    cout << "ФИО студента: " << stu_data.name << endl
        << "Группа: " << stu_data.group << endl
        << "Возраст: " << stu_data.age << endl
        << "Средний балл: " << stu_data.average << endl
        << "Стипендия: " << stu_data.scholarship << endl << endl;
}
void print_data_tab(students stu_data)
{
    cout << setiosflags(ios::left) << setw(sizeof (stu_data.group)) << stu_data.group << setw(sizeof (stu_data.name)) << stu_data.name << setw(4) << stu_data.age << setw(5) << stu_data.average << setw(6) << stu_data.scholarship << endl;
}
Лучшие ответы (1)
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
27.05.2014, 17:39     Возврат функцией массива структур
Посмотрите здесь:

Сортировка элементов массива структур шаблонной функцией - C++
Как отсортировать с помощью шаблонной функции по значению полей в массиве структур? Кто знает, подскажите пожалуйста. Программа, которую...

Возвращение функцией значения динамического массива структур - C++
Auto readfile() { ifstream file(file); int i = 0, color; Auto *A = new Auto; while (!file.eof()) { file &gt;&gt; A.name &gt;&gt;...

Возврат функцией экземпляра класса - C++
Подскажите, будет ли корректной с точки зрения выделения памяти и всего прочего такая запись: MyObject fun(....) { myObject Obj =...

Возврат функцией указателя на функцию - C++
Всем привет! У меня возникла такая проблема: класс имеет поле-указатель на функцию. В методе, который осуществляет доступ к этуму полю,...

Возврат массива - C++
Не спрашивайте зачем я это делаю, если можно просто использовать strcpy. char tostrcpy(char *to, char *from); int main(int i) { ...

Возврат массива из функции - C++
Здравствуйте. Не могу разобраться, почему при передачи массива из функции но не правильно передаётся. Вот результат.

Возврат массива из функции - C++
Есть задача: используя функции, вычислить количество элементов заранее введённых массивов, которые кратны Х, и переписать в отдельный...

После регистрации реклама в сообщениях будет скрыта и будут доступны все возможности форума.
Exzotick
0 / 0 / 0
Регистрация: 25.05.2014
Сообщений: 25
29.05.2014, 05:52  [ТС]     Возврат функцией массива структур #16
montkay, просто преподаватель так сказала. А вот фразу "заполнить массив структур, а потом просто в нужный момент обращаться к членам массива и указывать их значение" я не совсем понял. Можно примерчик?
montkay
10 / 10 / 8
Регистрация: 19.02.2014
Сообщений: 72
29.05.2014, 14:41     Возврат функцией массива структур #17
Exzotick, видно или преподаватель что-то другое имела ввиду, или она сама не понимает, для чего такое возвращающее значение. Тогда название функции будет таким: students * use_arr(students * pStud, int n), а возвращать функция будет return pStud;
Это самое адекватное, что могу предложить. Но это бессмысленно =(
По поводу вашего вопроса. В программе вы можете вызвать средний бал, к примеру, не через функцию, которая его возвращает, а следующим образом: students_arr[i].average;
Также можно любой член элементов массива структур вызвать таким образом (имя, группу, оценки и т.д.).
Exzotick
0 / 0 / 0
Регистрация: 25.05.2014
Сообщений: 25
29.05.2014, 15:44  [ТС]     Возврат функцией массива структур #18
montkay, почему-то у меня выдает ошибку "Необработанное исключение по адресу".
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
//7.4
#include <iostream>
#include <algorithm>
#include <windows.h>
#include <cstring>
#include <iomanip>
//#include <cstdio>
using namespace std;
 
const int name_size = 30, n = 6;
struct students
{
    char name[name_size];
    char group[n];
    int age;
    float average;
    float scholarship;
};
 
students* fill_arr(int);
void use_arr (students*);
students  fill_name(students);
students  fill_group(students);
int fill_age(students);
float fill_average(students);
float fill_scholaship(students);
void print_data(students);
void print_data_tab(students);
 
int main()
{
    SetConsoleCP(1251);
    SetConsoleOutputCP(1251);
    char choice;
    students *students_arr = NULL;// students* Pstud=NULL;
    int students_num;
    cout << "Заполните информацию о студентах \n1-ввести данные с клавиатуры \n2-использовать заготовку" << endl;
    cin >> choice;
    switch (choice)
    {
    case '1':
        cout << "Введите количество студентов: ";
        cin >> students_num;
        students_arr = fill_arr(students_num);
        break;
    case '2':
         use_arr (students_arr);
        students_num = 8;//sizeof (students_arr) / sizeof (students);
        break;
    }
    system("cls");
    cout << "\nИнформация о студентах: \n" << endl;
    int i, j; 
    for (i = 0; i < students_num; i++)
        for (j = 0; j<students_num - i - 1; j++)
            if (strcmp(students_arr[j].group, students_arr[j + 1].group) > 0)
                swap(students_arr[j], students_arr[j + 1]);
            else
            if (strcmp(students_arr[j].group, students_arr[j + 1].group) == 0)
                if (strcmp(students_arr[j].name, students_arr[j + 1].name) > 0)
                    swap(students_arr[j], students_arr[j + 1]);
    for ( i = 0; i < students_num; i++)
        print_data_tab(students_arr[i]);
    system("pause");
}
students* fill_arr(int students_num)
{
    students* students_arr = new students[students_num];
    for (int i = 0; i < students_num; i++)
    {
        students_arr[i] = fill_name(students_arr[i]);
        students_arr[i] = fill_group(students_arr[i]);
        students_arr[i].age = fill_age(students_arr[i]);
        students_arr[i].average = fill_average(students_arr[i]);
        students_arr[i].scholarship = fill_scholaship(students_arr[i]);
    }
    return students_arr;
}
void use_arr (students* Pstud)
{
    students student1 = { "Урманов Роман Сергеевич", "Б8120", 18, 5.0, 7500 },
        student2 = { "Спицын Вячеслав Валерьевич", "Б8120", 17, 4.5, 0 },
        student3 = { "Аристова Дарья Павловна", "Б8120", 18, 4.0, 0 },
        student4 = { "Иванов Петр Владимирович", "М6180", 22, 5.0, 9000 },
        student5 = { "Дорошин Сергей Александрович", "М6180", 22, 4.9, 2800 },
        student6 = { "Годенко Николай Борисович", "Б5216", 19, 4.3, 2400 },
        student7 = { "Афанасьев Виктор Иванович", "Б5216", 19, 4.0, 1900 },
        student8 = { "Галинов Вячеслав Иванович", "Б5216", 19, 3.8, 0 };
    students default_students_arr[] = { student1, student2, student3, student4, student5, student6, student7, student8 };
    for (int i=0; i<8; i++)
        Pstud[i]=default_students_arr[i];
}
students  fill_name(students stu_data)
{
    cout << "\nВведите имя студента: ";
    cin.get();
    gets_s(stu_data.name, sizeof (stu_data.name));
    return stu_data;
}
students fill_group(students stu_data)
{
    cout << "Введите группу: ";
    gets_s(stu_data.group, sizeof (stu_data.group));
    return stu_data;
}
int fill_age(students stu_data)
{
    cout << "Введите возраст студента: ";
    cin >> stu_data.age;
    return stu_data.age;
}
float fill_average(students stu_data)
{
    cout << "Введите средний балл студента: ";
    cin >> stu_data.average;
    return stu_data.average;
}
float fill_scholaship(students stu_data)
{
    cout << "Введите размер стипендии: ";
    cin >> stu_data.scholarship;
    return stu_data.scholarship;
}
void print_data(students stu_data)
{
    cout << "ФИО студента: " << stu_data.name << endl
        << "Группа: " << stu_data.group << endl
        << "Возраст: " << stu_data.age << endl
        << "Средний балл: " << stu_data.average << endl
        << "Стипендия: " << stu_data.scholarship << endl << endl;
}
void print_data_tab(students stu_data)
{
    cout << setiosflags(ios::left) << setw(sizeof (stu_data.group)) << stu_data.group << setw(sizeof (stu_data.name)) << stu_data.name << setw(4) << stu_data.age << setw(5) << stu_data.average << setw(6) << stu_data.scholarship << endl;
}
montkay
10 / 10 / 8
Регистрация: 19.02.2014
Сообщений: 72
29.05.2014, 20:01     Возврат функцией массива структур #19
Случай case '2' я подкорректировал немножко, также как ещё пару функций. Честно, потенциальных ошибок у вас очень много, по этому точно сказать причину возникновения сообщения "Необработанное исключение по адресу" не смогу сказать. Но вторая функция в switch (choice) у меня нормально работает.

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
#include <iostream>
#include <algorithm>
#include <windows.h>
#include <cstring>
#include <iomanip>
//#include <cstdio>
using namespace std;
 
const int name_size = 30, n = 6;
struct students
{
    char name[name_size];
    char group[n];
    int age;
    float average;
    float scholarship;
};
 
students* fill_arr(students*, int);
void use_arr (students*);
students  fill_name(students);
students  fill_group(students);
int fill_age(students);
float fill_average(students);
float fill_scholaship(students);
void print_data(students);
void print_data_tab(students);
 
int main()
{
    SetConsoleCP(1251);
    SetConsoleOutputCP(1251);
    char choice;
    students *students_arr = NULL;// students* Pstud=NULL;
    int students_num;
    cout << "Заполните информацию о студентах \n1-ввести данные с клавиатуры \n2-использовать заготовку" << endl;
    cin >> choice;
    switch (choice)
    {
    case '1':
        cout << "Введите количество студентов: ";
        cin >> students_num;
        students_arr = new students[students_num];
        students_arr = fill_arr(students_arr, students_num);
        break;
    case '2':
        students_num = 8;
        students_arr = new students[students_num];
         use_arr (students_arr);
        //sizeof (students_arr) / sizeof (students);
        break;
    }
    system("cls");
    cout << "\nИнформация о студентах: \n" << endl;
    int i, j; 
    for (i = 0; i < students_num; i++)
        for (j = 0; j<students_num - i - 1; j++)
            if (strcmp(students_arr[j].group, students_arr[j + 1].group) > 0)
                swap(students_arr[j], students_arr[j + 1]);
            else
            if (strcmp(students_arr[j].group, students_arr[j + 1].group) == 0)
                if (strcmp(students_arr[j].name, students_arr[j + 1].name) > 0)
                    swap(students_arr[j], students_arr[j + 1]);
    for ( i = 0; i < students_num; i++)
        print_data_tab(students_arr[i]);
    system("pause");
}
students* fill_arr(students * pStud, int students_num)
{
    for (int i = 0; i < students_num; i++)
    {
        pStud[i] = fill_name(pStud[i]);
        pStud[i] = fill_group(pStud[i]);
        pStud[i].age = fill_age(pStud[i]);
        pStud[i].average = fill_average(pStud[i]);
        pStud[i].scholarship = fill_scholaship(pStud[i]);
    }
    return pStud;
}
void use_arr (students* Pstud)
{
    students student1 = { "Урманов Роман Сергеевич", "Б8120", 18, 5.0, 7500 },
        student2 = { "Спицын Вячеслав Валерьевич", "Б8120", 17, 4.5, 0 },
        student3 = { "Аристова Дарья Павловна", "Б8120", 18, 4.0, 0 },
        student4 = { "Иванов Петр Владимирович", "М6180", 22, 5.0, 9000 },
        student5 = { "Дорошин Сергей Александрович", "М6180", 22, 4.9, 2800 },
        student6 = { "Годенко Николай Борисович", "Б5216", 19, 4.3, 2400 },
        student7 = { "Афанасьев Виктор Иванович", "Б5216", 19, 4.0, 1900 },
        student8 = { "Галинов Вячеслав Иванович", "Б5216", 19, 3.8, 0 };
    students default_students_arr[8] = { student1, student2, student3, student4, student5, student6, student7, student8 };
    for (int i=0; i<8; i++)
        Pstud[i]=default_students_arr[i];
}
students  fill_name(students stu_data)
{
    cout << "\nВведите имя студента: ";
    cin.get();
    gets_s(stu_data.name, sizeof (stu_data.name));
    return stu_data;
}
students fill_group(students stu_data)
{
    cout << "Введите группу: ";
    gets_s(stu_data.group, sizeof (stu_data.group));
    return stu_data;
}
int fill_age(students stu_data)
{
    cout << "Введите возраст студента: ";
    cin >> stu_data.age;
    return stu_data.age;
}
float fill_average(students stu_data)
{
    cout << "Введите средний балл студента: ";
    cin >> stu_data.average;
    return stu_data.average;
}
float fill_scholaship(students stu_data)
{
    cout << "Введите размер стипендии: ";
    cin >> stu_data.scholarship;
    return stu_data.scholarship;
}
void print_data(students stu_data)
{
    cout << "ФИО студента: " << stu_data.name << endl
        << "Группа: " << stu_data.group << endl
        << "Возраст: " << stu_data.age << endl
        << "Средний балл: " << stu_data.average << endl
        << "Стипендия: " << stu_data.scholarship << endl << endl;
}
void print_data_tab(students stu_data)
{
    cout << setiosflags(ios::left) << setw(sizeof (stu_data.group)) << stu_data.group << setw(sizeof (stu_data.name)) << stu_data.name << setw(4) << stu_data.age << setw(5) << stu_data.average << setw(6) << stu_data.scholarship << endl;
}
Exzotick
0 / 0 / 0
Регистрация: 25.05.2014
Сообщений: 25
31.05.2014, 15:03  [ТС]     Возврат функцией массива структур #20
Есть еще одна проблема. Функции для заполнения имени приходится возвращать всю структуру, потому что если ее описать как char* fill_name (students), то выдает ошибку. Можно ли сделать, чтобы она возвращала только одно поле структуры (stu-data.name)?

Добавлено через 1 час 50 минут
montkay, я тут маленько поиздевался над вашим кодом и понял, что ошибка возникает, если в case 2 не делать динамического выделения памяти. Почему это необходимо, если в функции use_arr мы создаем статический массив, и присваиваем его pStud?
Kuzia domovenok
1890 / 1745 / 118
Регистрация: 25.03.2012
Сообщений: 5,924
Записей в блоге: 1
31.05.2014, 15:21     Возврат функцией массива структур #21
Цитата Сообщение от Exzotick Посмотреть сообщение
montkay, я тут маленько поиздевался над вашим кодом и понял, что ошибка возникает, если в case 2 не делать динамического выделения памяти. Почему это необходимо, если в функции use_arr мы создаем статический массив, и присваиваем его pStud?
ты что, вообще не понимаешь? Блин! Ты в этой функции копируешь default_students_arr в pStud
то есть из одного места в памяти в другое, ё-моё!
И и источник и приёмник копируемых данных должен быть выделенной памятью! иначе ты скопируешь default_students_arr неизвестно куда! А надо, чтобы было известно, т.е. заранее выделить место для копии default_students_arr, чтобы это место было такого же размера!
Exzotick
0 / 0 / 0
Регистрация: 25.05.2014
Сообщений: 25
31.05.2014, 16:44  [ТС]     Возврат функцией массива структур #22
Можно ли это сделать, не копируя один массив в другой, а присвоить указатель на массив другому указателю?
Kuzia domovenok
1890 / 1745 / 118
Регистрация: 25.03.2012
Сообщений: 5,924
Записей в блоге: 1
31.05.2014, 18:35     Возврат функцией массива структур #23
Exzotick, нет, так как этот массив - локальный внутри этой функции и указатель на него будет действовать только внутри неё.
После возвращения из функции этот массив (default_students_arr) будет "уничтожен", точнее затёрт данными из других функций, а может и не затёрт, в любом случае сохранность данных не гарантируется.

Поэтому нужно поэлементно копировать данные в память, которая была заранее выделена до вызова этой функции и соответственно гарантированно сохранится и после выхода из неё.
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
31.05.2014, 23:21     Возврат функцией массива структур
Еще ссылки по теме:

Возврат массива из функции - C++
В объекте есть массив int state;, который мне нужно из него вытащить. Вижуал показывал ошибку, когда я пытался вернуть указатель state в...

Возврат массива из класса - C++
вот класс в котором есть массив а class Population1 { public: Population1(int,int); ~Population1(); int ProvLife(int,...

Возврат массива из функции - C++
Программа должна переводить числа с 10 системы в двоичную... но почемуто выводит некорректно... Вот код... #include &lt;iostream&gt; using...

Возврат массива из функции - C++
Здравствуйте, Не пойму почему не работает данный код. Пишет cannot convert 'std::string*' to 'int*' in return По теории я жду...

Возврат индексов двумерного массива - C++
Нужно получить индексы минимального элемента в матрице. Не понимаю, как передать индексы.Как-то через указатели? int min(int A,...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
montkay
10 / 10 / 8
Регистрация: 19.02.2014
Сообщений: 72
31.05.2014, 23:21     Возврат функцией массива структур #24
Если функция char* fill_name (students) будет возвращать return pStud->name;, то не должно быть ошибок.
Если создать статический массив внутри функции, то он умрет в этой же функции, в отличии от динамически выделенной памяти.
Yandex
Объявления
31.05.2014, 23:21     Возврат функцией массива структур
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2017, vBulletin Solutions, Inc.
Рейтинг@Mail.ru