Цель лекции: изучить указатели на структуры, операции над указателями на структуры, взаимодействие структур и функций, указатели как компоненты структур, научиться решать задачи с использованием указателей на структуры на языке C++.
Структура – это совокупность переменных, объединенных одним именем, предоставляющая общепринятый способ совместного хранения информации. В отличие от массива, всегда состоящего из однотипных элементов, компоненты структуры могут быть разных типов и все должны иметь различные имена.
Указатель на структуру объявляется точно так же, как и указатель на данные простых типов: используется операция '*' и указывается тип данных. Тип данных структуры указывается заданием ключевого слова struct и имени шаблона этой структуры.
Синтаксис:
ИмяСтруктурногоТипа *ИмяУказателяНаСтруктуру
Например:
struct goods *p_goods; struct student *p_stu1, *p_stu2;
Указатели на структуры могут вводиться и для безымянных (не имеющих имен)
Например:
struct {
char *name;
int age;
} *person; //указатель на структуру
Если структура объявлена с помощью typedef, то при определении указателей название этого типа может использоваться без служебного слова struct.
Например:
complex *cc, *ss, comp;
При определении указателя на структуру он может быть инициализирован. Корректно в качестве инициализирующего значения применять адрес структурного объекта того же типа, что и тип определяемого указателя.
Например:
struct particle {
double mass;
float coord[3];
} dot[3], point, *pinega;
//Инициализация указателей
struct particle *p_d=dot[1], *pinta=point;
Значение указателя на структуру может быть определено и с помощью присваивания.
Например:
pinega=dot[0];
При определении элемента структуры запрещено указание в качестве элемента самого себя (через структурный объект).
Например:
struct STUD { //некорректное объявление поля структуры
STUD t;
} a, b;
Однако элемент структуры может быть указателем на определяемую структуру.
Например:
struct STUD { //корректное объявление поля структуры
STUD *pt;
} a, b;
Кроме того, допустимо неполное определение типа структуры, если ее указатель является элементом другой структуры.
Например:
struct A; //неполное определение структурного типа
struct B {struct A *pta;};
struct A {struct B *ptb;};
При определении
Например:
struct part {
double modul;
struct cell *element_cell;
struct part *element_part;
};
struct cell {
long summa;
struct cell *one;
struct part *two;
};
Указатель на структуру обеспечивает доступ к ее элементам двумя способами:
(*УказательНаСтруктуру).ИмяЭлемента
или
УказательНаСтруктуру->ИмяЭлемента
В первом случае круглые скобки необходимы, чтобы учесть
Во втором случае используется операция "стрелка" ( -> ), которая называется операцией косвенного выбора элемента структурного объекта, адресуемого указателем.
Например:
(*pinega). эквивалентно pinega ->
(*pinega).coord[0] эквивалентно pinega -> coord[0]
Пример 1.
#include "stdafx.h"
#include <stdio.h>
#include <string.h>
#include <iostream>
using namespace std;
struct student {
char name[10];
char surname[15];
int age;
} stud;
//переменная stud объявлена как структура типа student
int _tmain(int argc, _TCHAR* argv[]) {
struct student *s; // указатель на структуру student
s=stud; // инициализация указателя
strcpy(s->name,"Larry");
//обращение как к указателю на структуру
strcpy(s->surname,"Johnson");
(*s).age=34; //обращение как к переменной
printf("\n Имя: %s \n Фамилия: %s \n Возраст = %i",
s->name,s->surname,s->age);
system("pause");
return 0;
}
Эти операции не отличаются от операций над другими указателями на данные. Исключение составляет операция "стрелка" ( -> ). Если присвоить указателю на структуру конкретного ++ или -- ), можно равномерно "перемещаться" по массиву структур.
Пример 2. Вычислить сумму заданного количества комплексных чисел, представленных в программе массивом структур.
#include "stdafx.h"
#include <iostream>
using namespace std;
#include <stdio.h>
struct complex {//Опредение структуры
float x;
float y;
}array[]={1.0,2.0,3.0,-4.0,-5.0,-6.0,-7.0,-8.0};
struct complex summa = {0.0, 0.0};
struct complex *point = array[0];
int _tmain(int argc, _TCHAR* argv[]) {
int i;
int k;
k=sizeof(array)/sizeof(array[0]);
for (i=0; i<k; i++){
summa.x+=point->x;
summa.y+=point->y; }
printf("\n Сумма: real=%f, \t imag=%f", summa.x, summa.y);
system("pause");
return 0;
}
Пример 3. Программа считывает системное время компьютера и переводит его во время по Гринвичу.
#include "stdafx.h"
#include <iostream>
using namespace std;
#include <time.h>
int _tmain(int argc, _TCHAR* argv[]) {
struct tm {
int tm_sec; //Секунды
int tm_min; //Минуты
int tm_hour; //Часы (0-23)
int tm_mday; //День месяца (1-31)
int tm_mon; //Месяц (0-11)
int tm_year; //Год (календарный год минус 1900)
int tm_wday; //День недели (0-6; Воскресенье = 0)
int tm_yday; //День года (0-365)
int tm_isdst;
//0, если переход на летнее время не используется
};
time_t t;
struct tm *gmt, *area;
t = time(NULL);
//Преобразует дату и время в структуру
area=localtime(t);
printf("Секунды: %d\n", area->tm_sec);
printf("Минуты: %d\n", area->tm_min);
printf("Часы: %d\n", area->tm_hour);
printf("День: %d\n", area->tm_mday);
printf("Месяц: %d\n", area->tm_mon);
printf("Год: %d\n", area->tm_year);
printf("День недели: %d\n", area->tm_wday);
printf("День года: %d\n", area->tm_yday);
printf("Местное время: %s", asctime(area));
//Преобразуем структуру в строку
gmt=gmtime(t);
//Преобразует дату и время во время по Гривинчу
printf("Время по Гринвичу: %s", asctime(gmt));
system("pause");
return 0;
}
Для взаимодействия структур и функций имеются две основные возможности: структура может быть возвращаемым функцией значением и структура может использоваться в
Например:
//Определение структурного типа
struct person {
char *name;
int age;
};
//Прототип функции struct person f (int N);
//Прототип функции struct person *ff (void);
//Прототип функции void fff (struct person str);
//Прототип функции void ffff (struct person *pst);
При вызове функции fff() выделяется память для формального параметра, т.е. для вспомогательного объекта типа struct person. В этот объект переносится значение str. Далее выполняются действия, предусмотренные операторами fff(). Эти действия не могут изменять структуру, использованную в качестве
В случае, когда параметром служит указатель на объект ffff() можно изменить ту структуру вызывающей функции, которая адресуется фактическим параметром .
Если функция не изменяет структуру, то такую структуру можно передать по значению.
Пример 4. Отображение полей структуры на экране.
#include "stdafx.h"
#include <iostream>
using namespace std;
struct book {
char title[40];
char authors[30];
char publishing_house[25];
int year;
int pages;
};
void show_book(book b) {
cout << "Название: "<< b.title<<"\n";
cout << "Автор: "<< b.authors<<"\n";
cout << "издательство: "<< b. publishing_house<<"\n";
cout << "Год: "<< b.year<<"\n";
cout << "Количество страниц: " << b.pages<<"\n";
}
int _tmain(int argc, _TCHAR* argv[]) {
book a={"Программирование на языке Си", "Подбельский В.В.",
"Финансы и статистика", 2004, 600};
show_book(a);
system("pause");
return 0;
}
Если обработка структуры в функции связана с изменением содержимого полей, то такую структуру необходимо передавать по указателю или по ссылке.
Пример 5.
#include "stdafx.h"
#include <iostream>
using namespace std;
struct book {
char title[40];
char authors[30];
char publishing_house[15];
int year;
int pages;
};
void input_book(book *b){ //структура передается по указателю
cout << "Название: ";
cin >> b->title;
cout << "Автор: ";
cin >> b->authors;
cout << "Издательство: ";
cin >> b->publishing_house;
cout << "Год: ";
cin >> b->year;
cout << "Количество страниц: ";
cin >> b->pages;
}
int _tmain(int argc, _TCHAR* argv[]) {
book a,*pa=a;
input_book(pa);
system("pause");
return 0;
}
Пример 6.
#include "stdafx.h"
#include <iostream>
using namespace std;
struct book {
char title[40];
char authors[30];
char publishing_house[15];
int year;
int pages;
};
void input_book(book b) { //структура передается по ссылке
cout << "Название: ";
cin >> b.title;
cout << "Автор: ";
cin >> b.authors;
cout << "Издательство: ";
cin >> b.publishing_house;
cout << "Год: ";
cin >> b.year;
cout << "Количество страниц: ";
cin >> b.pages;
}
int _tmain(int argc, _TCHAR* argv[]) {
book a;
input_book(a);
system("pause");
return 0;
}
Функции могут не только получать структуры в качестве своих параметров, но и возвращать результаты в виде структур. Это означает, что функция, возвращающая значение, может иметь в качестве результата своей работы совокупность значений полей соответствующей структуры.
Пример 7. Функции g1, g2 и g3 возвращают структуру.
#include "stdafx.h"
#include <iostream>
using namespace std;
struct ss {
int a;
float b;
};
ss g1(ss v){ //параметр - значение
v.a=7;
v.b=8;
return v;
}
ss g2(ss v){ //параметр - ссылка
v.a=v.b+7;
v.b=v.a+8;
return v;
}
ss g3(const ss v){ //параметр - константная ссылка
ss q;
q.a=v.b+7;
q.b=v.a+8;
return q;
}
int _tmain(int argc, _TCHAR* argv[]) {
ss x1,y1={1,2};
ss x2,y2={3,4};
ss x3,y3={5,6};
x1=g1(y1);
cout << "x1=" << x1.a << "; " << x1.b << "\n";
cout << "y1=" << y1.a << "; " << y1.b << "\n";
y1=g1(y1);
cout << "x1=" << x1.a << "; " << x1.b << "\n";
cout << "y1=" << y1.a << "; " << y1.b << "\n";
x2=g2(y2);
cout << "x2=" << x2.a << "; " << x2.b << "\n";
cout << "y2=" << y2.a << "; " << y2.b << "\n";
x3=g3(y3);
cout << "x3=" << x3.a << "; " << x3.b << "\n";
cout << "y3=" << y3.a << "; " << y3.b << "\n";
y3=g3(y3);
cout << "x3=" << x3.a << "; " << x3.b << "\n";
cout << "y3=" << y3.a << "; " << y3.b << "\n";
system("pause");
return 0;
}
Значение указателя на структуру – адрес расположения элементов структуры.
Структура – это совокупность переменных, объединенных одним именем, предоставляющая общепринятый способ совместного хранения информации.
Структура как значение функции является результатом работы функции, возвращающей совокупность значений полей соответствующей структуры.
Структура как параметр функции является передаваемыми фактическими значениями соответствующих полей структуры.
Указатель на структуру – это указатель на расположение элементов структуры в памяти.
-> ).Цель работы: изучить указатели на структуры, операции над указателями на структуры, взаимодействие структур и функций, указатели как компоненты структур, научиться решать задачи с использованием указателей на структуры на языке C++.
При выполнении лабораторной работы для каждого задания требуется написать программу на языке С++, в которой выполнена разработка структуры в соответствии с постановкой задачи, ввод данных элементов
Теоретические сведения.
Ознакомьтесь с материалом лекции 16.
Задания к лабораторной работе.
Выполните приведенные ниже задания.
Введите проходной балл на специальность: 255 Введите количество абитуриентов: 5 Сведения о 1 абитуриенте Фамилия: Петров Имя: Федор Отчество: Степанович Число баллов по первому предмету: 84 Число баллов по второму предмету: 76 Число баллов по третьему предмету: 95 Результат: зачислен ...
Указания к выполнению работы.
Каждое задание необходимо решить в соответствии с изученными методами объявления и обработки данных структур в языке С++. При объявлении
Следует реализовать каждое задание в соответствии с приведенными этапами:
Требования к отчету.
Отчет по лабораторной работе должен соответствовать следующей структуре.
Контрольные вопросы
Для получения официальных документов о завершении программы дополнительного профессионального образования (удостоверения о повышении квалификации, дипломов о профессиональной переподготовке и MBA) необходимо предоставить:
Внимание! Вы можете не заказывать доставку бумажной версии официального документы, а скачать его в электронном виде и распечатать самостоятельно. Информация о выданном документе в течение 1 месяца загружается в Федеральную информационную систему «Федеральный реестр сведений о документах об образовании и (или) о квалификации, документах об обучении» - ФИС ФРДО.
Доступ на новый сайт осуществляется с использованием адреса электронной почты, который был указан вами при регистрации на "старом". Мы постарались перенести все ваши данные с прежнего ресурса, однако не исключена вероятность потери части информации.
При возникновении проблемы со входом, воспользуйтесь функцией сброса пароля
Если вы обнаружите несоответствия, пожалуйста, сообщите нам.