Как обращаться к полям структуры. Структуры в си и их передача

Структура — это агрегатный тип данных, так как может содержать в себе разнотипные элементы. Синтаксис объявления структуры в С++ отличается от C. Хотя версия C остается правильной для C++. Получается, что в С++ можно двумя стилями объявления структур пользоваться, а в языке C — только одной. Смотрим синтаксис объявления структуры в языке С++:

Struct Name { type atrib; // остальные элементы структуры } structVar1, structVar2, ...;

  • struct — ключевое слово, которое начинает определение структуры
  • Name — имя структуры
  • type — тип данных элемента структуры
  • atrib — элемент структуры
  • structVar1-2 — структурные переменные

Объявление структуры всегда должно начинаться с ключевого слова struct . Необязательно, чтобы структура имела имя, но тогда такая структура обязательно должна иметь структурные переменные, объявленные между закрывающей фигурной скобкой и точкой с запятой, строка 5. Обязательно в объявлении структуры должны присутствовать фигурные скобочки, они обрамляют тело структуры, в котором объявляются её атрибуты (элементы), строка 3. Структурные переменные, при объявлении структуры, указывать необязательно, строка 5.

Так как структура это тип данных, то, для того, чтобы использовать этот тип данных, необходимо объявить структурную переменную, а вместо типа данных указать имя структуры.

struct_name structVariable;

Синтаксис объявления структуры в языке Си:

Typedef struct name { type atrib1; type atrib2; // остальные элементы структуры... } newStructName structVar;

Синтаксис объявления структуры в языке Си предполагает два варианта. Первый, опустить ключевое слово typedef , при этом имя newStructName тоже не используется, и имя структуры, тогда обязательно необходимо при объявлении структуры использовать структурные переменные — structVar , строка 6. Смотрим пример:

Struct name structVar;

Или вы можете воспользоваться typedef , для объявления псевдонима структуры newStructName , псевдоним:

NewStructName structVar;

В любом случае, если вы хотите, объявить указатель на структуру внутри структуры, вы должны использовать первый синтаксис:

Struct name *struct_instance; // указатель на структуру

Объявление указателя на структуру

Синтаксис объявления указателя на структуру в Си неоднозначен. В Си, если вы не используете typedef при определении структуры, то, в обязательном порядке необходимо использовать структурные переменные, между закрывающейся фигурной скобочкой и точкой с запятой.
В C++, этого не требуется. Чтобы объявить указатель на структуру, в С++ вы просто перед именем структурной переменной ставите символ указателя — * .

StructName *structVar; // указатель на структуру structName

NewStructName *structVar; // newStructName должно быть объявлено с typedef

или так, тоже для СИ:

Struct name *structVar;

Доступ к элементам структуры

Доступ к элементам структуры так же прост, как использование символа «точка». Предположим. что у нас есть структурная переменная с именем car и у нее есть элемент с именем speed , к которому, мы сейчас получим доступ:

Car.speed;

Примечание: такой способ доступа к элементам структуры работает только в том случае, когда структура не является указателем на структуру.

Доступ к элементам указателя на структуру

Чтобы получить доступ к элементам структуры, через указатель на структуру, вместо оператора «точка», используйте оператор стрелка -> :

CarPtr->speed;

P.S.: Всем владельцам Android-смартфонов представляю хорошую подборку программ GPS навигаторов для android . В списке представлено около 20 программных продуктов, вы можете любой скачать и установить на свой девайс. Все программы абсолютно бесплатные.

А теперь только представьте — вы сами можете создавать, своего рода, типы данных, которые вам необходимы и с которыми вам будет удобно работать! И это несложно!

Структура — это, некое объединение различных переменных (даже с разными типами данных), которому можно присвоить имя. Например можно объединить данные об объекте Дом: город (в котором дом находится), улица, количество квартир, интернет(проведен или нет) и т.д. в одной структуре. В общем, можно собрать в одну совокупность данные обо всем, что угодно, точнее обо всем, что необходимо конкретному программисту. Всем сразу стало понятно:)

Если вы только приступаете к знакомству со структурами в С++, сначала, вам необходимо ознакомиться с синтаксисом структур в языке С++ . Рассмотрим простой пример, который поможет познакомиться со структурами и покажет, как с ними работать. В этой программе мы создадим структуру, создадим объект структуры, заполним значениями элементы структуры (данные об объекте) и выведем эти значения на экран. Ну что же, приступим!

#include using namespace std; struct building //Создаем структуру! { char *owner; //здесь будет храниться имя владельца char *city; //название города int amountRooms; //количество комнат float price; //цена }; int main() { setlocale (LC_ALL, "rus"); building apartment1; //это объект структуры с типом данных, именем структуры, building apartment1.owner = "Денис"; //заполняем данные о владельце и т.д. apartment1.city = "Симферополь"; apartment1.amountRooms = 5; apartment1.price = 150000; cout << "Владелец квартиры: " << apartment1.owner << endl; cout << "Квартира находится в городе: " << apartment1.city << endl; cout << "Количество комнат: " << apartment1.amountRooms << endl; cout << "Стоимость: " << apartment1.price << " $" << endl; return 0; }

В строках 4 — 10 мы создаем структуру. Чтобы ее объявить используем зарезервированное слово struct и даем ей любое, желательно логичное, имя. В нашем случае — building . С правилами именования переменных, вы можете ознакомиться в этой статье . Далее открываем фигурную скобку { , перечисляем 4 элемента структуры через точку с запятой; , закрываем фигурную скобку } и в завершении ставим точку с запятой; . Это будет нашим шаблоном (формой) структуры.

В строке 16 объявляем объект структуры. Как и для обычных переменных, необходимо объявить тип данных. В этом качестве выступит имя нашей созданной структуры — building .

Как же заполнить данными (инициализировать) элементы структуры? Синтаксис таков: Имя объекта далее оператор точка. и имя элемента структуры. Например: apartment1.owner . Таким образом, в строках 18-21 присваиваем данные элементам структуры.

И так, данные мы внесли. Следующий вопрос: «Как к ним обратиться, как работать и использовать их в программе?» Ответ — «Очень просто — так же, как и при инициализации, используя точку. и имя элемента структуры». В строках 23 — 26 выводим заполненные элементы структуры на экран.

И вот что мы увидим в результате, когда скомпилируем нашу программу:

Владелец квартиры: Денис Квартира находится в городе: Симферополь Количество комнат: 5 Стоимость: 150000 $

Что ещё важно знать:

  • Объект структуры можно объявить до функции main() . Это выглядело бы так:
struct building { char *owner char *city; int amountRooms; float price; }apartment1; //объявление объекта типа building
  • Инициализировать структуру можно и таким способом:
building apartment1 = {"Денис", "Симферополь", 5, 150000};

но так делают крайне редко;

  • Структуру можно вкладывать в другие структуры (это мы рассмотрим в следующем примере).

Дополним предыдущий пример, чтобы увидеть дополнительные возможности работы со структурами.

Пример:

#include using namespace std; struct date //создаем еще одну структуру, чтобы вложить ее в структуру building // дата постройки { char *month; // Месяц постройки дома int year; // Год }; struct building { char *owner; char *city; int amountRooms; float price; date built; //вкладываем одну структуру в определение второй }; void show(building object) //создаем функцию, которая принимает структуру, как параметр { cout << "Владелец квартиры: " << object.owner << endl; cout << "Квартира находится в городе: " << object.city << endl; cout << "Количество комнат: " << object.amountRooms << endl; cout << "Стоимость: " << object.price << " $" << endl; cout << "Дата постройки: " << object.built.month << " " << object.built.year << endl; } int main() { setlocale (LC_ALL, "rus"); building apartment1; apartment1.owner = "Денис"; apartment1.city = "Симферополь"; apartment1.amountRooms = 5; apartment1.price = 150000; apartment1.built.month = "январь"; apartment1.built.year = 2013; struct building *pApartment; //это указатель на структуру pApartment = &apartment1; //Обратите внимание, как нужно обращаться к элементу структуры через указатель //используем оператор -> cout << "Владелец квартиры: " << pApartment->owner << endl; cout << "Квартира находится в городе: " << pApartment->city << endl; cout << "Количество комнат: " << pApartment->amountRooms << endl; cout << "Стоимость: " << pApartment->price << " $" << endl; cout << "Дата постройки: " << pApartment->built.month << " " << pApartment->built.year << "\n\n\n"; building apartment2; //создаем и заполняем второй объект структуры apartment2.owner = "Игорь"; apartment2.city = "Киев"; apartment2.amountRooms = 4; apartment2.price = 300000; apartment2.built.month = "январь"; apartment2.built.year = 2012; building apartment3 = apartment2; //создаем третий объект структуры и присваиваем ему данные объекта apartment2 show(apartment3); cout << endl << endl; return 0; }

Коментарии по коду программы:

Строка 17 — создание объекта built типа date в определении структуры building . Строки 42 — 43 : создаем указатель на структуру struct building *pApartment; и далее присваиваем ему адрес уже созданного и заполненного данными объекта pApartment = &apartment1; . Обращаясь к элементам структуры через указатель мы используем оператор -> (тире и знак >) . Это видно в строках 47 — 51.

В строке 62 показано, как можно инициализировать структуру. А именно, можно создать новый объект структуры и присвоить ему одним целым, уже созданный и заполненный данными, объект. В функцию show() передаем объект структуры, как параметр — строка 64. Результат:

Владелец квартиры: Денис
Квартира находится в городе: Симферополь
Количество комнат: 5
Стоимость: 150000 $
Дата постройки: январь 2013
Владелец квартиры: Игорь
Квартира находится в городе: Киев
Количество комнат: 4
Стоимость: 300000 $
Дата постройки: январь 2012
Для продолжения нажмите любую клавишу. . .

Разобрав этот пример, мы увидели на практике следующее:

  • структуру можно вкладывать в другую структуру;
  • увидели, как создаётся указатель на структуру;
  • как нужно обращаться к элементу структуры через указатель. А именно, используя оператор -> ; В примере это было так: apartment0->owner , но можно и так (*apartment0).owner . Круглые скобки, во втором случае, обязательны.
  • данные одной структуры можно присвоить другой структуре;
  • можно структуру передать в функцию, как параметр (кстати, элементы структуры так же можно передавать в функцию, как параметры).

В дополнение ко всему, следует отметить, что функции могут так же возвращать структуры в результате своей работы. Например:

Building Set() { building object; // формирование объекта //... код функции return object; }

Вот так, вкратце, мы познакомились со структурами в языке С++, попрактиковались на примерах и узнали основы. Это только начало!

Последнее обновление: 09.10.2017

Ранее для определения классов мы использовали ключевое слово class . Однако C++ предоставляет еще один способ для определения пользовательских типов, который заключается в использовании структур. Данный способ был унаследован языком С++ еще от языка Си.

Структура в языке C++ представляет собой производный тип данных, который представляет какую-то определенную сущность, также как и класс. Нередко структуры применителько к С++ также называют классами. И в реальности различия между ними не такие большие.

Для определения структуры применяется ключевое слово struct , а сам формат определения выглядит следующим образом:

Struct имя_структуры { компоненты_структуры };

Имя_структуры представляет произвольный идентификатор, к которому применяются те же правила, что и при наименовании переменных.

После имени структуры в фигурных скобках помещаются Компоненты_структуры , которые представляют набор описаний объектов и функций, которые составляют структуру.

Например, определим простейшую структуру:

#include #include struct person { int age; std::string name; }; int main() { person tom; tom.name = "Tom"; tom.age = 34; std::cout << "Name: " << tom.name << "\tAge: " << tom.age << std::endl; return 0; }

Здесь определена структура person , которая имеет два элемента: age (представляет тип int) и name (представляет тип string).

После определения структуры мы можем ее использовать. Для начала мы можем определить объект структуры - по сути обычную переменную, которая будет представлять выше созданный тип. Также после создания переменной структуры можно обращаться к ее элементам - получать их значения или, наоборот, присваивать им новые значения. Для обращения к элементам структуры используется операция "точка":

Имя_переменной_структуры.имя_элемента

По сути структура похожа на класс, то есть с помощью структур также можно определять сущности для использования в программе. В то же время все члены структуры, для которых не используется спецификатор доступа (public, private), по умолчанию являются открытыми (public). Тогда как в классе все его члены, для которых не указан спецификатор доступа, являются закрытыми (private).

Кроме того мы можем инициализировать структуру, присвоив ее переменным значения с помощью синтаксиса инициализации:

Person tom = { 34, "Tom" };

Инициализация структур аналогична инициализации массивов: в фигурных скобках передаются значения для элементов структуры по порядку. Так как в структуре person первым определено свойство, которое представляет тип int - число, то в фигурных скобках вначале идет число. И так далее для всех элементов структуры по порядку.

При этом любой класс мы можем представить в виде структуры и наоборот. Возьмем, к примеру, следующий класс:

Class Person { public: Person(std::string n, int a) { name = n; age = a; } void move() { std::cout << name << " is moving" << std::endl; } void setAge(int a) { if (a > 0 && a < 100) age = a; } std::string getName() { return name; } int getAge() { return age; } private: std::string name; int age; };

Данный класс определяет сущность человека и содержит ряд приватных и публичных переменных и функции. Вместо класса для определения той же сущности мы могли бы использовать структуру:

#include #include struct user { public: user(std::string n, int a) { name = n; age = a; } void move() { std::cout << name << " is moving" << std::endl; } void setAge(int a) { if (a > 0 && a < 100) age = a; } std::string getName() { return name; } int getAge() { return age; } private: std::string name; int age; }; int main() { user tom("Tom", 22); std::cout << "Name: " << tom.getName() << "\tAge: " << tom.getAge() << std::endl; tom.setAge(31); std::cout << "Name: " << tom.getName() << "\tAge: " << tom.getAge() << std::endl; return 0; }

И в плане конечного результата программы мы не увидели бы никакой разницы.

Когда использовать структуры? Как правило, структуры используются для описания таких данных, которые имеют только набор публичных атрибутов - открытых переменных. Например, как та же структура person, которая была определена в начале статьи. Иногда подобные сущности еще называют аггрегатными классами (aggregate classes).

Структуры

Как вам должно быть уже известно, классы относятся к ссылочным типам данных. Это означает, что объекты конкретного класса доступны по ссылке, в отличие от значений простых типов, доступных непосредственно. Но иногда прямой доступ к объектам как к значениям простых типов оказывается полезно иметь, например, ради повышения эффективности программы. Ведь каждый доступ к объектам (даже самым мелким) по ссылке связан с дополнительными издержками на расход вычислительных ресурсов и оперативной памяти.

Для разрешения подобных затруднений в C# предусмотрена структура , которая подобна классу, но относится к типу значения, а не к ссылочному типу данных. Т.е. структуры отличаются от классов тем, как они сохраняются в памяти и как к ним осуществляется доступ (классы - это ссылочные типы, размещаемые в куче, структуры - типы значений, размещаемые в стеке), а также некоторыми свойствами (например, структуры не поддерживают наследование). Из соображений производительности вы будете использовать структуры для небольших типов данных. Однако в отношении синтаксиса структуры очень похожи на классы.

Главное отличие состоит в том, что при их объявлении используется ключевое слово struct вместо class. Ниже приведена общая форма объявления структуры:

struct имя: интерфейсы { // объявления членов }

где имя обозначает конкретное имя структуры.

Как и у классов, у каждой структуры имеются свои члены: методы, поля, индексаторы, свойства, операторные методы и события. В структурах допускается также определять конструкторы, но не деструкторы. В то же время для структуры нельзя определить конструктор, используемый по умолчанию (т.е. конструктор без параметров). Дело в том, что конструктор, вызываемый по умолчанию, определяется для всех структур автоматически и не подлежит изменению. Такой конструктор инициализирует поля структуры значениями, задаваемыми по умолчанию. А поскольку структуры не поддерживают наследование, то их члены нельзя указывать как abstract, virtual или protected.

Объект структуры может быть создан с помощью оператора new таким же образом, как и объект класса, но в этом нет особой необходимости. Ведь когда используется оператор new, то вызывается конструктор, используемый по умолчанию. А когда этот оператор не используется, объект по-прежнему создается, хотя и не инициализируется. В этом случае инициализацию любых членов структуры придется выполнить вручную.

Давайте рассмотрим пример использования структур:

Using System; namespace ConsoleApplication1 { // Создадим структуру struct UserInfo { public string Name; public byte Age; public UserInfo(string Name, byte Age) { this.Name = Name; this.Age = Age; } public void WriteUserInfo() { Console.WriteLine("Имя: {0}, возраст: {1}",Name,Age); } } class Program { static void Main() { UserInfo user1 = new UserInfo("Alexandr", 26); Console.Write("user1: "); user1.WriteUserInfo(); UserInfo user2 = new UserInfo("Elena",22); Console.Write("user2: "); user2.WriteUserInfo(); // Показать главное отличие структур от классов user1 = user2; user2.Name = "Natalya"; user2.Age = 25; Console.Write("\nuser1: "); user1.WriteUserInfo(); Console.Write("user2: "); user2.WriteUserInfo(); Console.ReadLine(); } } }

Обратите внимание, когда одна структура присваивается другой, создается копия ее объекта. В этом заключается одно из главных отличий структуры от класса. Когда ссылка на один класс присваивается ссылке на другой класс, в итоге ссылка в левой части оператора присваивания указывает на тот же самый объект, что и ссылка в правой его части. А когда переменная одной структуры присваивается переменной другой структуры, создается копия объекта структуры из правой части оператора присваивания.

Поэтому, если бы в предыдущем примере использовался класс UserInfo вместо структуры, получился бы следующий результат:

Назначение структур

В связи с изложенным выше возникает резонный вопрос: зачем в C# включена структура, если она обладает более скромными возможностями, чем класс? Ответ на этот вопрос заключается в повышении эффективности и производительности программ. Структуры относятся к типам значений, и поэтому ими можно оперировать непосредственно, а не по ссылке. Следовательно, для работы со структурой вообще не требуется переменная ссылочного типа, а это означает в ряде случаев существенную экономию оперативной памяти.

Структура в Си - тип данных, предназначенный для размещения значения разного типа в одном объекте. Полезен, когда необходимо объединить несколько переменных с разными типами под одним именем. Делают программу более компактной, ею удобней управлять. Структура имеет схожие особенности с массивами и классами.

Массивы

Прежде чем говорить о структуре в Си, нужно описать массив.

Существуют массивы одномерные, двумерные, трехмерные. Одномерный - это такой, у которого есть только одна строка с заполненными значениями. Двумерный - одномерный массив, внутри которого находятся другие одномерные массивы.

Обычный массив в Си записывается так: int a = {1, 2, 3, 4}.

Видим, что a - имя, int - тип данных, внутри фигурных скобок { } находятся значения, между квадратными скобками указывается длина, то есть количество элементов. Количество элементов является статическим, равняется 4. Это означает, что если в этом примере пользователь добавит пятое значение, компилятор выдаст ошибку. Если изначально не известно количество, они могут быть добавлены позже, но в квадратных скобках не ставится значение.

Двумерный объявляется похожим образом. Например, массив, который содержит 5 элементов-массивов, при этом каждый содержит по 3 элемента объявляется так: int a.По аналогии с одномерным добавлять ничего нельзя, чтобы не получить ошибку компилирования.

Различают динамические и статические. Статический - это такой, который вмещает фиксированное количество данных, то есть имеет постоянную длину. Под динамическим понимается тот, размер которого не ограничивается, он может меняться во время выполнения программы. Инициализация динамического массива происходит без указания точного количества.

Классы

Класс и структура похожи по между собой, но отличаются некоторыми нюансами. Что это такое? Это абстракция, описывающая методы еще не существующего объекта. После создания объект или, как он называется по-другому, экземпляр класса имеет конкретные свойства. Методы могут использоваться внутри, снаружи или при наследовании.

Класс объявляется так:

class /*class name*/

/* спецификатор доступа private обозначает, что управление методами возможно только внутри класса*/

/* делает свойства доступными для других частей кода */

/* наследуемые классы получают возможность использовать эти свойства */

Что такое структура в языке Си

Предназначена для хранения несколько типов данных. Например, чтобы создать каталог журналов, нужно иметь список с такими параметрами:

  • дата издания;
  • номер выпуска;
  • название;
  • стоимость.

Для решения этой задачи можно было бы применить массивы.

Объявляем массив с датами int date, номерами int number, названиями char title, стоимостью int price.

Обращаясь по индексу, мы получаем требуемую информацию. Вывод информации о произведении под номером 3 выглядит так: cout << “дата выпуска: ” date “, номер: ” number “, название: ” title “, стоимость: “ price).

Структура упрощает запись, описывается следующим образом:

Видим одно из главных преимуществ - присутствуют разные типы переменных. Программист не просто экономит время - он упрощает код, в дальнейшем ему будет намного проще работать.

Объявление

Структуры в Си играют очень важную роль - объединение данных различного типа.

Для начала нужно указать имя структуры и свойства.

Struct - ключевое слово, оно начинает объявление, name - имя, type - тип данных, member - имя элемента.

Объявляется так:

name name2, где name - заданное при создании структуры имя, а name2 - имя переменной.

Объявить переменные можно на этапе создания.

Первый и второй пример равносильны друг другу.

Если есть необходимость объявить несколько переменных, они перечисляются через запятую.

} name2, name3, name4.

Инициализация

После объявления структуру в Си необходимо инициализировать.

name2.member=”a”;

Инициазация может происходить при создании.

char member = “a”;

У структуры такой же синтаксис, как у класса. У них практически одинаковое поведение, возможности. Все, что находится в теле класса, по умолчанию недоступно для использования другими объектами.

У структуры все наоборот - все поля и методы являются публичными. Вручную можно задать модификатор доступа private и таким образом открыть доступ другим функциям или классам.

Массивы - это множество компонентов одного типа. Они располагаются рядом с друг другом, обращение к каждому из них осуществляется по числовому индексу. Существуют одномерные массивы, двумерные, трехмерные.

У одномерного только одна строка и n-e количество элементов. Объявление выглядит так:

Массив структур в Си объявляется так:

В этом примере мы создали MyStruct с элементом целочисленного типа под именем "а". Объявляем переменную obj1 - она является массивом, состоит из 10 элементов.

При объявлении нескольких массивов одного типа используется MyStruct obj1, obj2, инициализация происходит во время объявления. Выглядит так:

Создание массива структур с динамическим выделением памяти выглядит точно также, как создание простого динамического массива. Для этого применяется указатель на структуру Си.

Указатель - это переменная, которая не содержит значения, а указывает на ту переменную, которая имеет какое-то значение. Соответственно, указатель содержит адрес этой переменной, на которую ссылается. Например, ptr = &var1 означает, что переменной со знаком амперсанда присвоен только адрес на переменную, но не само значение. Теперь все значения var1 доступны через переменную-указатель ptr.

Операция * отсылает к содержимому ячейки, на которую указывает переменная после этого символа. Например, *ptr говорит о том, что здесь содержатся значения, взятые из ячейки с адресом к ptr.

Чтобы выделить память для динамических переменных, используют операцию new.

У нас есть

Выделяем участок памяти, заносим туда некое значение MyStruct * point = new MyStruct;

Для удаления динамических переменных используем операцию delete. Чтобы освободить место, вводим delete p;

Доступ

Все элементы по умолчанию являются публичными, поэтому другие классы их могут использовать. Чтобы задать или изменить некоторые значения, сначала нужно обратиться к элементу и только потом произвести соответствующие действия.

Создаем myStruct с именем переменной b.

struct myStruct {

Обращаемся к fio:

и задаем произвольное значение. Например, b.fio = “Ivanov”.

Рассмотрим такой пример.

struct myStruct {

{ "Иванов", 456756 },

{ "Петров", 632345 }

В данном примере у нас есть массив структур со строками и числами. Чтобы вывести на экран фамилию Иванов, используем следующее:

cout << myStruct tel.fio;

Когда захотим получить значение 456756, выполняем cout << myStruct tel.num.

Структура и функции

Может использоваться, как аргумент функция в структуре в Си.

struct myStruct {

Имеем переменную value, строку text на 100 символов. Создаем переменную menu типа myStruct: myStruct menu. В следующем примере функция принимает указатель на структуру как аргумент, а в теле безымянной функции происходит инициализация этих переменных.

void item(myStruct menu)

sprintf(menu.text,"One item");

Заключение

Структура - это такой набор, наподобие массива, но при этом все элементы могут быть разного типа. Очень похожа на класс, но отличается тем, что свойства по умолчанию доступны для использования другими классами, то есть имеют спецификатор public.

Создается с помощью ключевого слова struct, а внутри фигурных скобок { } указываются свойства.

Объявление происходит на этапе создания или после.