Кроме классов для создания своих типов данных можно использовать структуры, которые унаследованы языком С++ от языка Си. Структура в C++ представляет собой производный тип данных, который представляет какую-то определенную сущность, также как и класс. Нередко структуры применителько к С++ также называют классами. И в реальности различия между ними не такие большие. Структура также может определять переменные, функции, конструкторы, деструкторы. Однако обычно структуры служат для хранения каких-то общедоступных данных в виде публичных переменных. Для остальных сценариев используются классы.
Для определения структуры применяется ключевое слово struct, а сам формат определения выглядит следующим образом:
struct имя_структуры
{
компоненты_структуры
};
Имя_структуры представляет произвольный идентификатор, к которому применяются те же правила, что и при наименовании переменных.
После имени структуры в фигурных скобках помещаются компоненты структуры - переменные и функции.
Например, определим простейшую структуру:
#include <iostream>
#include <string>
struct person
{
unsigned age;
std::string name;
};
int main()
{
person tom;
tom.name = "Tom";
tom.age = 34;
std::cout << "Name: " << tom.name << "\tAge: " << tom.age << std::endl;
}
Здесь определена структура person, которая имеет две переменных: name
(представляет тип string) и age (представляет тип unsigned).
После определения структуры мы можем ее использовать. Для начала мы можем определить объект структуры - по сути обычную переменную, которая будет представлять выше созданный тип. Также после создания переменной структуры можно обращаться к ее элементам - получать их значения или, наоборот, присваивать им новые значения. Для обращения к элементам структуры используется операция "точка":
имя_переменной_структуры.имя_элемента
По сути структура похожа на класс, то есть с помощью структур также можно определять сущности для использования в программе. В то же время все члены структуры, для которых не используется спецификатор доступа (public, private), по умолчанию являются открытыми (public). Тогда как в классе все его члены, для которых не указан спецификатор доступа, являются закрытыми (private).
Кроме того мы можем инициализировать структуру, присвоив ее переменным значения с помощью синтаксиса инициализации:
person tom{ 34, "Tom" };
Инициализация структур аналогична инициализации массивов: в фигурных скобках передаются значения для элементов структуры по порядку. Так как в структуре person первым определено свойство, которое представляет тип unsigned - число, то в фигурных скобках вначале идет число. И так далее для всех элементов структуры по порядку.
При этом любой класс мы можем представить в виде структуры и наоборот. Возьмем, к примеру, следующий класс:
#include <iostream>
#include <string>
class Person
{
public:
Person(std::string name, unsigned age): name{name}, age{age}
{ }
void print()
{
std::cout << "Name: " << name << "\tAge: " << age << std::endl;
}
private:
std::string name;
unsigned age;
};
int main()
{
Person bob{"Bob", 42};
bob.print();
}
Данный класс определяет сущность человека и содержит ряд приватных и публичных переменных и функции. Вместо класса для определения той же сущности мы могли бы использовать структуру:
#include <iostream>
#include <string>
struct person
{
public:
person(std::string name, unsigned age): name{name}, age{age}
{
}
void print()
{
std::cout << "Name: " << name << "\tAge: " << age << std::endl;
}
private:
std::string name;
unsigned age;
};
int main()
{
person bob{"Bob", 42};
bob.print();
}
И в плане конечного результата программы мы не увидели бы никакой разницы.
Когда использовать структуры? Как правило, структуры используются для описания таких данных, которые имеют только набор публичных атрибутов - открытых переменных. Например, как та же структура person, которая была определена в начале статьи. Иногда подобные сущности еще называют аггрегатными классами (aggregate classes).