Использование потоков (отличия от процессов)
Основной причиной необходимости потоков является выполнением большинством приложений существенного количества действий, некоторые из которых могут время от времени блокироваться. Схему программы можно существенно упростить. если разбить приложение на несколько последовательных потоков. запущенных в квазистационарном режиме.
Это утверждение являлось аргументом в пользу существования процессов. Мы можем рассуждать на языке параллельных процессов вместо прерываний, таймеров и переключателей контекста. В случае потоков придется добавить еще один элемент: возможность совместного использования параллельными объектами адресного пространства и всех содержащихся в нем элементов. Для определенных приложений эта возможность является определяющей, и в таких ситуациях схема параллельных процессов (с разными адресными пространствами не подходит).
Еще одним аргументом в пользу потоков является легкость их создания и уничтожения (потому что с потоком не связаны никакие ресурсы). В большинстве систем на создание потока уходит примерно в 100 раз меньше времени, чем на создание процесса. Это свойство особенно полезно, если необходимо динамическое и быстрое изменение количества потоков.
Третьим аргументом является производительность. Концепция потоков не дает увеличения производительности, если все они ограничены возможностями процессора. Но когда имеется единовременная потребность в выполнении большого объема вычислений и операций ввода-вывода, наличие потоков позволяет совмещать эти виды деятельности во времени, тем самым увеличивая общую скорость работы приложения.
Приведем пример использования потоков. Возьмем в качестве примера текстовый редактор. Большинство текстовых редакторов выводят текст на экран монитора в том виде, в котором он будет напечатан. В частности, разрывы строк и страниц находятся на своих местах, и пользователь может при необходимости их откорректировать (например, удалить неполные строки вверху и внизу страницы).
Представим, что пользователь пишет книгу. С точки зрения автора проще всего хранить всю книгу в одном единственном файле, чтобы легче было искать отдельные разделы, выполнять глобальную замену и т.п. С другой стороны, можно хранить каждую главу в отдельном файле. Но было бы крайне неудобно хранить каждый раздел и параграф в отдельном файле - в сотни глобальных изменений пришлось бы редактировать сотни файлов. Например, если предполагаемый стандарт ххх был утвержден только перед отправкой книги в печать, придется изменять “Черновой стандарт ххх” на “Стандарт ххх” в последнюю минуту. Эта операция делается одной командой в случае одного файла и, напротив, займет очень много времени, если если придется редактировать каждый из 300 файлов, на которые разбита книга.
Теперь представим себе, что произойдет, если пользователь удалит одно предложение на первой странице документа, в котором 800 страниц. Пользователь перечитал это предложение и решил исправить предложение на 600-ой странице. Он дает текстовому редактору команду перейти на 600 страницу (например, задав поиск фразы, встречающейся только на этой странице). Текстовому редактору придется переформатировать весь документ вплоть до 600-ой странице, поскольку до форматирования он не будет знать, где начинается эта страница. Это может занять достаточно много времени и вряд ли обрадует пользователя.
В этом случае помогут потоки. Пусть текстовый редактор написан в виде двух поточной программы. Один поток взаимодействует с пользователем, а другой форматирует документ в фоновом режиме. Как только предложение на первой странице было удалено пользователем, интерактивный поток дает команду фоновому потоку переформатировать весь документ. В то время как первый поток продолжает отслеживать и выполнять команды с клавиатуры и мыши - предположим, прокручивает первую страницу, - второй поток быстро переформатирует книгу. Немного везения - и форматирование будет закончено раньше, чем пользователь захочет перейти к 600-ой странице, и тогда команда будет выполнена мгновенно.
Можно создать и третий поток. Большинство текстовых редакторов автоматически сохраняет редактируемый текст раз в несколько минут, чтобы пользователь не лишился плодов работы целого дня в случае аварийного завершения программы, отказа системы или перебоев с питанием. Этим будет заниматься третий поток, не отвлекая два оставшихся.
Если бы программа была однопоточной, тогда при каждом сохранении файла все команды с клавиатуры и мыши игнорировались до окончания дисковой операции. У пользователя это бы создало впечатления низкой производительности. В качестве альтернативы команды с клавиатуры и мыши могут прерывать сохранение файла, обеспечивая высокую производительность, но приводя к усложнению программной модели, управляемой прерываниями. Программная модель с тремя потоками гораздо проще. Первый поток взаимодействует с пользователем, второй при необходимости переформатирует документ, а третий периодически сохраняет на диск содержимое оперативной памяти.
Очевидно, что в этом случае модель с тремя процессами не подойдет, поскольку всем трем необходимо работать с одним и тем же документом. Три же потока совместно используют общую память и все три имеют доступ к документу.