Arraybuffer И Sharedarraybuffer В Javascript, Часть 1: Ускоренный Курс По Управлению Памятью

Автоматическое управление памятью.

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

С другой стороны, за удобство приходится платить.

JavaScript — это как раз тот случай, когда управление памятью происходит автоматически, однако появление ArrayBuffer и SharedArrayBuffer меняет ситуацию.



ArrayBuffer и SharedArrayBuffer в JavaScript, часть 1: ускоренный курс по управлению памятью

Чтобы понять, что именно ArrayBuffer и SharedArrayBuffer привносят в JS-разработку, и почему эти объекты появились в языке, предлагаем начать с самого начала, а именно с разговора об управлении памятью.



Память и работа с ней

Оперативную память можно рассматривать как набор ячеек.

Или как куча почтовых ящиков, которые есть в офисах, или как шкафчики в детском саду, где дети могут хранить свои вещи.

Если кому-то нужно оставить что-то для одного из детей, он может положить это в свой шкафчик.



ArrayBuffer и SharedArrayBuffer в JavaScript, часть 1: ускоренный курс по управлению памятью

Шкафчики, в один из которых кто-то собирается что-то положить Рядом с каждым из полей есть число, которое применительно к оперативной памяти является адресом.

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

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

Насколько именно это зависит от конкретной компьютерной архитектуры.

Этот размер называется размером слова памяти.

Обычно это что-то вроде 32 или 64 бит. Для простоты изложения мы будем использовать 8-битные слова.



ArrayBuffer и SharedArrayBuffer в JavaScript, часть 1: ускоренный курс по управлению памятью

Блок из восьми ячеек Если вам нужно поместить, например, число 2 в одну из этих 8-битных ячеек, это очень легко сделать, так как числа легко преобразуются в двоичная система счисления .



ArrayBuffer и SharedArrayBuffer в JavaScript, часть 1: ускоренный курс по управлению памятью

Десятичное число 2 преобразуется в двоичное 00000010, которое находится в ячейке памяти.

Что делать, если вам нужно поместить в ячейку что-то, кроме числа? Например, латинская буква H? В данном случае нам нужно найти способ представить букву в виде числа.

Для того чтобы это сделать, букву необходимо как-то закодировать, например использовать кодировку UTF-8 .

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

Буква после преобразования также может храниться в 8-битной ячейке.



ArrayBuffer и SharedArrayBuffer в JavaScript, часть 1: ускоренный курс по управлению памятью

Буква Н преобразуется с помощью энкодера в десятичное число 72, которое после преобразования в двоичное помещается в ячейку памяти.

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



Автоматическое управление памятью

При программировании на JavaScript вам не нужно беспокоиться о том, что происходит с памятью.

Эта часть системы абстрагирована от разработчика.

Это значит, что он не работает напрямую с памятью.

Вместо этого движок JS выступает в роли посредника.

Он отвечает за управление памятью.



ArrayBuffer и SharedArrayBuffer в JavaScript, часть 1: ускоренный курс по управлению памятью

Набор ячеек памяти за забором, доступ к которым контролируется JS-движком Допустим, некоторый JS-код, например библиотека React, хочет создать переменную.



ArrayBuffer и SharedArrayBuffer в JavaScript, часть 1: ускоренный курс по управлению памятью

React просит движок JS создать строковую переменную.

Получив запрос на создание переменной и присвоение ей значения, механизм JS пропускает это значение через кодировщик для создания его двоичного представления.



ArrayBuffer и SharedArrayBuffer в JavaScript, часть 1: ускоренный курс по управлению памятью

Движок JS преобразует строковую переменную в ее двоичное представление.

Затем механизм ищет место в памяти, куда можно поместить полученное двоичное представление.

Это называется распределением памяти.



ArrayBuffer и SharedArrayBuffer в JavaScript, часть 1: ускоренный курс по управлению памятью

JS-движок ищет свободное место для двоичных данных Затем движок проверяет, доступна ли переменная где-нибудь в программе.

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



ArrayBuffer и SharedArrayBuffer в JavaScript, часть 1: ускоренный курс по управлению памятью

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

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

Автоматическое управление памятью может облегчить жизнь разработчикам.

Но это приводит к дополнительной нагрузке на систему.

Иногда эта нагрузка оказывает непредсказуемое влияние на производительность.



Ручное управление памятью

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

Например, давайте представим, как бы работал React, если бы он был написан на C (собственно, сейчас он похож, благодаря Веб-сборка , уже Может быть ).

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



ArrayBuffer и SharedArrayBuffer в JavaScript, часть 1: ускоренный курс по управлению памятью

Версия React для WebAssembly работает напрямую с памятью.

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

Например, это может быть подсистема, кодирующая и декодирующая байты.

Этот вспомогательный код называется средой выполнения приложения.

В JavaScript эту роль играет движок JS.

ArrayBuffer и SharedArrayBuffer в JavaScript, часть 1: ускоренный курс по управлению памятью

Кодировщик символов добавлен в файл .

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

Это не означает, что задача управления памятью полностью лежит на программисте.

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

Например, в C он отслеживает доступные адреса памяти, сохраняя их в списке свободной памяти.



ArrayBuffer и SharedArrayBuffer в JavaScript, часть 1: ускоренный курс по управлению памятью

Список свободной памяти отражает текущее состояние системы.

Здесь вы можете использовать функцию malloc (ее название — сокращение от Memory Allocation, то есть выделение памяти), чтобы попросить среду выполнения найти адреса блоков памяти, подходящих для хранения данных.

После выделения памяти соответствующие адреса будут удалены из списка свободной памяти.

Когда данные, хранящиеся в памяти, больше не нужны, пришло время использовать команду free для освобождения памяти.

Тогда адреса освободившихся блоков памяти снова появятся в списке свободной памяти.

Программисту необходимо самому решить, когда именно вызывать вышеупомянутые функции.

Поэтому то, о чем мы говорим, называется «ручным управлением памятью».

Разработчику может быть очень сложно решить, когда следует очищать различные области памяти.

Неправильное время освобождения памяти может привести к ошибкам или даже проблемам безопасности.

Если память не освобождается, рано или поздно это приведет к ее заполнению.



Полученные результаты

Именно во избежание человеческих ошибок многие современные языки используют автоматическое управление памятью.

Однако при таком подходе страдает производительность системы и эффективность использования памяти.

Подробнее об этом в следующий раз.

Уважаемые читатели! Как вы думаете, что изменилось бы в разработке JavaScript, если бы язык поддерживал ручное управление памятью без каких-либо вспомогательных механизмов, таких как сбор мусора? Теги: #программирование #JavaScript #WebAssembly #управление памятью

Вместе с данным постом часто просматривают: