Параллельное программирование: описание, технология, задачи и преимущества
Идеи параллельных вычислений и обработки информации долгое время были уделом специалистов и достаточно значительной проблемой в плане реализации. Особенное значение и массовый интерес они приобрели не так давно.
Можно утверждать, что именно развитие интернет-технологий дало новый импульс и параллельное программирование приобрело новые потребительские качества. Это обусловило не только очевидный прогресс технологий и языков программирования. Это реально создало обратное влияние на понимание параллельного процесса.
Технологии параллельного программирования кардинально изменились. Начальное применение компьютерных устройств как вычислителей плавно перешло в использование их как обработчиков информации. Жесткие архитектурные решения уступили место семантике и гибкому распределению программного функционала по «аппаратным исполнителям».
Параллельные вычисления: смысл и реализация
Первоначально основы параллельного программирования закладывались в архитектуре вычислительных устройств. Была предложена классификация на основе понятия потока.
Последовательность команд, данных, функционально полных последовательных алгоритмов рассматривалась как объект, который можно исполнить параллельно с другим подобным объектом.
При таком подходе сущность каждого объекта не имела значения, но имело значение такое разбиение на параллельные участки кода, которые могли быть исполнены независимо, то есть данные на входе и выходе каждого потока не пересекались. Каждый поток не зависел от другого потока, а если он нуждался в данных от другого потока, то переходил в режим ожидания.
Такая идея привела к четырем архитектурам:
- SISD - простой поток команд и простой поток данных;
- MISD - множественный поток команд и простой поток данных;
- SIMD - простой поток команд и множественный поток данных;
- MIMD - многовариантный поток команд и множественный поток данных.
Эти идеи существовали относительно долго, но не привели к особым эффектам. Сегодня - это история трудного начала. Но это начало создало фундамент для современных достижений.
Недосток архитектурной идеи: отсутствие семантики
Как и конструкция жилого здания, архитектура вычислительной системы не касалась семантики. Как будут жить жильцы в здании, какой они смогут сделать ремонт и какую решат установить мебель, никогда не волновало строителей.
В самом начале системы параллельного программирования также не придавали значения алгоритму, который должен будет исполняться. Процессор сам разделял код и данные на участки, которые исполнял параллельно. Это давало заметный прирост производительности, но волновала, в частности:
- проблема разделения памяти между процессами;
- логика ожидания одним потоком результатов работы другого потока;
- механизм защиты памяти одного процесса от другого процесса;
- логика взаимодействия независимых процессоров, ядер;
- логика переключения между процессами;
- обмен данными «на лету» между процессами...
Разработчики больше ориентировались на аппаратные механизмы, что лишало параллельное многопоточное программирование возможности иметь семантику и не давало возможности программисту управлять процессами адекватно решаемой задаче.
Промышленное применение параллельности
Первое назначение компьютеров: сложные математические вычисления, промышленное применение и всё, что не касалось повседневной жизни, мобильности и интернета. Естественно, когда задачи параллельного программирования столь «ограничены», трудно ожидать интересных достижений.
Когда компьютеры стали продукцией массового применения, появился интернет и мобильные девайсы, требования к параллельности резко изменились и разработчикам пришлось кардинально менять стиль и скорость работы.
Первой ласточкой стали идеи обмена сообщениями между процессами. Интерфейс передачи сообщений MPI, параллельное программирование, потребности разработчиков и ожидания потребителей стали промежуточным этапом.
Windows и ей подобные системы закрепили эту идею и фактически сделали её законодательной нормой: параллельность и обмен сообщениями - это одно целое для всякой многопроцессорной, многоядерной, а по существу - для любой информационной системы.
От вычислений к обработке информации
Вычисления - это частный случай обработки информации. От параллельных архитектур, реализованных аппаратно к мобильным программным решениями: языки параллельного программирования реально стали достоянием истории. Современный язык обеспечивает реальную параллельность процессов, но для этого вовсе не обязательно иметь специальные операторы в синтаксисе или дополнительные библиотеки к языку.
«Промышленное» мышление в программировании, когда параллельное многопоточное программирование является целью, а не средством, сущестовало недолго. К каким фундаментальным результатам оно привело, сказать трудно. Однако нет сомнений в том, что программирование, которое было до эпохи интернет-программирования, стало основанием для отличных идей и хорошего потенциала современных языков и инструментальных средств.
Аппаратная составляющая
Первые компьютеры были монстрами, занимали четверть футбольного поля и выделяли столько тепла, что можно было спокойно обогреть небольшой населенный пункт, а не тратиться на постройку электростанций.
Следующее поколение компьютеров - персональные. Персоналки помещались на рабочем столе, а сотовые телефоны можно было носить на плече. Персоналки быстро изменились и приобрели современный вид, дали жизнь ноутбукам, планшетам и иным девайсам, а сотовые телефоны превратились в удобные многофункциональные смартфоны.
Изготовитель электронных компонентов в полную силу задействовал идеи прошлых лет, и параллельное программирование теперь существует на любом девайсе, вне зависимости от того, как к нему относится тот или иной разработчик программного обеспечения.
Сегодня количество ядер процессора, количество процессоров, уровень технологии, параллельность и функциональность кода критичны даже непосвященному пользователю.
Математический аппарат
Теория графов и массового обслуживания, как частные варианты, расчеты прямых и кривых для визуального отображения информации, как основа для видеокарт, обусловили четкую функциональность аппаратной составляющей, которая обрела статус и качество стандарта.
Можно говорить о количестве ядер в процессоре девайса, но процессор для отображения информации уже давно один и занимается своим делом. Видеокарта может иметь не один процессор и не одно ядро, но математический аппарат в нее имплантирован.
Процессор компьютера только формулирует простые команды на отображение информации или выборку её из видеопамяти, остальное - забота процессора видеокарты.
Собственно, математические вычисления уже давно были выделены из основного процессора в математический сопроцессор. В настоящее время это тоже норма вещей.
Фактически, рассматривая параллельное программирование на аппаратном уровне, можно представить современный компьютер, как совокупность параллельно работающих подсистем, которые предоставляют разработчику все необходимое для реализации всевозможных идей распределенной и параллельной обработки информации.
Принято считать, что фундаментальные аппаратные ресурсы для любой информационной системы находятся в идеальном состоянии и развиваются стабильно. Программисту остается только лишь писать качественный код.
Объектно-ориентированное программирование
При классическом программировании алгоритм решения - последовательность команд. При объектно-ориентированном программировании алгоритм решения - это совокупность объектов, каждый из которых имеет свои данные и свои методы.
Посредством методов объекты взаимодействуют друг с другом, а значит, как они будут исполняться аппаратной частью компьютера (девайса), программиста волнует меньше всего. Однако логика взаимодействия объектов - сфера компетенции программиста.
Информационная система, построенная на объектах, как правило, это некоторая система абстракций, допускающая различные варианты создания объектов различного типа и назначения. Будучи описанными на уровне абстракций, информационные системы могут обеспечивать различные комбинации объектов, включая создание последними самих себя.
Проще говоря, при объектно-ориентированном программировании трудно привязать исполнение объекта ядру или процессору для обеспечения его параллельного исполнения. Это существенно замедлит общий процесс. Один объект может существовать в десятке экземпляров, но это не означает, что существование каждого должно ждать, когда существование предыдущего завершится.
Кластеры и распределенная параллельность
Современное интернет-программирование для решения сложных и уникальных задач предлагает единственно возможное решение: ручная работа! Для обыденного и коммерческого применения используются многочисленные и разнообразные системы управления сайтами.
Характерная черта интернет-программирования:
- неопределенность;
- множественность;
- одновременность.
Создавая сайт, программист (чаще коллектив программистов) не знает, сколько посетителей должен будет принимать веб-ресурс, но знает точно, что всем клиентам сайт должен обеспечить одинаковое и минимальное время отклика на любое действие.
Очевидное решение: разместить сайт на множестве серверов или кластеров по территориальному признаку, и тогда каждый регион будет обслуживать конкретный сервер. Но современный сайт не только предоставляет информацию, но и использует её. Например, интернет-магазин не может торговать воздухом и, если одно изделие было приобретено в Москве, оно должно исчезнуть со склада для потребителя во Владивостоке.
Сделать распределенную обработку информации фактически означает обеспечить параллельную работу одного и того же функционала на различных серверах для различных групп потребителей при том условии, что действия потребителей отражаются в системе и не противоречат друг другу.
В таком контексте параллельное программирование приобретает совершенно иной смысл. Если раньше разработчик ставил во главу угла механизм реализации параллельности, не имея ввиду саму задачу, то сегодня разработчика меньше всего волнует, как реализована параллельность на уровне аппаратуры или инструментального средства, его интересует параллельность на уровне клиентов, то есть самой задачи, самой сферы применения веб-ресурса.
Кластер, как вариант параллельной реализации
Принято считать, что кластер - это разновидность распределенной параллельной обработки информации. Это совокупность компьютеров, соединенных высокоскоростными линиями связи.
Характерно, что кластер может состоять из различных компьютеров, которые могут находится в различных местах планеты, но по определению: кластер - это единое целое. Системы управления сайтами, основанные на кластерах, не дают возможности непосредственного управления составляющими кластер компьютерами, но они обеспечивают скрытое параллельное управление всеми процессами на уровне решаемой задачи.
Разработчик, работая с кластерами, может планировать и реализовывать собственный функционал параллельной распределенной обработки информации. Это очень существенный прогресс в современной разработке.
«Жизнь» современного объекта
Сегодня очень трудно найти веб-ресурс, основанный на статических или динамических страницах, формируемых целиком. Современный сайт - это совокупность динамичных страниц, которые заполняются параллельно по технологии AJAX.
Современная динамичная страница состоит из различного контента, каждая часть страницы может быть загружена самостоятельно, в зависимости от поведения посетителя. В этом контексте объектно-ориентированное программирование показывает, что далеко не весь его потенциал раскрыт.
Действительно, поведение клиента приводит к запросу на сервер для обновления части страницы. Запрос отрабатывается, создается масса объектов, сервер отсылает результат обратно. Следующий запрос... опять масса объектов, опять отсылается результат. Фактически получается, что при современном подходе сервер «не помнит» что, когда и куда он послал. При каждом обращении он повторяет минимально необходимые действия, создает все те же системы объектов.
Программист не может изменить логику работы сервера, но он легко может эмулировать собственный сервер на доступном ему, физическом уровне. Получится совершенно новое качество распределенной параллельной обработки информации.
Собственный сервер будет держать нужную систему объектов в актуализированном состоянии, что значительно ускорит обработку запросов как от одной страницы, так и от всех страниц, открытых во всем интернет-пространстве для конкретного веб-ресурса.