Найти в Дзене
Alexei Strelnikov

Почему Apple настаивает на использовании структур (struct)?

С самого начала появления языка Swift компания Apple настаивала на том, чтобы разработчики регулярно использовали структуры. В статье Apple говорится: "Дополнительные возможности, которые поддерживают классы, достаются ценой повышенной сложности. В качестве общего руководства предпочитайте структуры, потому что о них легче рассуждать, и используйте классы, когда они уместны или необходимы. На практике это означает, что большинство пользовательских типов данных, которые вы определяете, будут структурами и перечислениями." В этой статье я хотел бы рассказать об основных причинах, по которым Apple рекомендует это делать. Потокобезопасность Безопасность потоков - важная тема для понимания и внедрения в код, поскольку она может привести к серьезным ошибкам в вашем приложении. Вероятно, самая распространенная ошибка - это гонки данных. Гонка данных - это когда как минимум два потока обращаются к одним и тем же данным, и один из этих потоков выполняет операцию записи. Гонки данных, как извест
Оглавление

С самого начала появления языка Swift компания Apple настаивала на том, чтобы разработчики регулярно использовали структуры. В статье Apple говорится:

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

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

Потокобезопасность

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

Когда два потока обращаются к одним и тем же данным, это называется общим изменяемым состоянием. Это может произойти только со ссылочными типами (классами), потому что экземпляры класса, к которым обращаются из двух разных мест, указывают на одно и то же место в памяти. Структуры не имеют такой проблемы, потому что они являются типами значений. Типы значений копируются при присвоении или передаче в функцию. Это устраняет общее изменяемое состояние и, следовательно, устраняет гонки данных!

Иногда необходимо разделяемое изменяемое состояние. Однако Apple ясно дает понять в приведенном выше заявлении, что о структурах "легко рассуждать". Это потому, что они не разделяют состояние. Вы знаете, что изменение значения структуры влияет только на локальное состояние. Это огромное преимущество структур.

Оптимизация

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

Когда мы имеем дело со ссылочными типами, мы также должны беспокоиться о количестве ссылок. Хотя Swift обрабатывает процесс удержания и освобождения данных, если мы структурируем наш код определенным образом, мы можем привести к тому, что данные никогда не будут освобождены, потому что мы не обработали ссылки должным образом. Это называется циклами удержания. Нам не нужно беспокоиться о циклах удержания с типами значений, потому что здесь нет ссылок, которые нужно подсчитывать!

Шаблонный код

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

Резюме

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

Эта заметка является переводом оригинальной статьи Пола Онила Why does Apple push for structs?