2

У меня есть 5 функций, которые нужно запускать в отдельном потоке. Grand Central Dispatch должен быть более эффективным, чем потоки, поэтому я решил использовать его. Каждая функция имеет бесконечный цикл while - while(true) - который работает в течение всего времени программы. Таким образом, функция не возвращается, пока программа не существует. Дело в том, что GCD не запускает очереди одновременно - он запускает каждый queu один за раз. Когда первый queu завершается, он начинает вторую очередь. Если я помещаю каждую функцию в очередь, запускается только одна из них, потому что Grand Central Dispatch будет ждать, пока первая вернется, чтобы запустить следующую, но функция никогда не вернется (поскольку это бесконечный цикл while). Есть ли способ использовать GCD с бесконечными функциями цикла? Или я должен просто использовать потоки?Использование Grand Central Dispatch с бесконечными циклами?

Xcode 3.2.6 на Mac OSX Snowleopard 10.6.8.

+3

Ваши петли while() должны (a) не быть ожиданными; они не должны зацикливаться, если у них нет реальной работы. И (б), они вообще не должны существовать! Вы должны использовать другую конструкцию, чтобы ждать, пока работа будет доступна. Нитки дороги и расточительны. Даже бездействующие потоки отходов. – bbum

+0

@bbum Мои потоки не заняты, они постоянно извлекают информацию и обновляют ее. Если потоки плохие, есть ли у вас какие-либо другие предложения, которые я мог бы использовать вместо этого, чтобы постоянно получать информацию на протяжении всей программы? – fdh

+1

Что такое источник данных? То есть сеть? Другие темы? и т.д...? – bbum

ответ

2

Звучит так же, как вы используете dispatch_sync. Посмотрите на dispatch_async.

https://developer.apple.com/library/mac/documentation/Performance/Reference/GCD_libdispatch_Ref/Reference/reference.html#//apple_ref/c/func/dispatch_async

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

+1

Dispatch_async все еще не работает параллельно друг другу – fdh

+2

@Farhad Neo является правильным, и вы ошибаетесь. Возможно, вы не отправляете асинхронный вызов в фоновый режим? – NJones

+0

@NJones от Apple: «Важно помнить, что очереди не являются панацеей для замены потоков. Модель асинхронного программирования, предлагаемая очередями, подходит в ситуациях, когда латентность не является проблемой. Хотя очереди предлагают способы настройки приоритета выполнения задач в очереди, более высокие приоритеты выполнения не гарантируют выполнение задач в определенное время. Поэтому потоки по-прежнему являются более подходящим выбором в случаях, когда вам требуется минимальная задержка, например, при воспроизведении аудио и видео ». – fdh

2

Пункт Grand Central Dispatch предназначен для выполнения задач, которые должны выполняться асинхронно, но не нуждающихся в потоке для одновременной работы, может быть эффективно поставлен в очередь без появления дополнительных потоков.

Однако, если ваша функция должна выполняться непрерывно в течение срока действия программы, вы должны продолжать использовать потоки: вот почему они существуют, и есть случаи, когда они вполне разумны.

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

Я могу быть более полезным, если вы укажете, что это ваши функции, и чего вы пытаетесь достичь.

+0

Спасибо. Я создаю монитор активности, такой как программа, и мои функции непрерывно извлекают статистику (например, использование процессора, использование памяти и т. Д.). Я хочу, чтобы данные были в режиме реального времени и непрерывны, поэтому я не хочу вызывать его в течение каждых X секунд, чтобы обновить его. Есть ли у вас какие-либо другие предложения или какие-либо потоки будут моим лучшим вариантом? – fdh

+0

Я бы не слишком плохо относился к использованию потоков (я чувствую себя хуже, когда постоянно запрашиваю статистику, что будет довольно грубо на системных ресурсах). GCD все еще может работать для вас, если хотите. Если у вас есть функция enqueue сама (или иначе организует ее периодическое размещение в очереди), она не будет работать непрерывно, но всякий раз, когда она появляется в очереди (которая должна быть почти непрерывной). Это не должно быть «каждую секунду» (это может быть намного чаще, если вы пожелаете). Также имейте в виду, что потоки также не работают непрерывно; они работают в удовольствие от планировщика. –

4

Мальчик, много путаных/conflciting ответов до сих пор!

Во-первых, нет причин для использования здесь. Никто. Использование GCD, даже для «длительных» операций, отлично. Если все, что вы делаете из указанных операций, - это чтение данных, а затем что-то делать с данными, то вы должны обязательно использовать источники отправки или dispatch_io, поскольку для этого они предназначены, и они могут значительно упростить ваш код, а также создавать только потоки по мере необходимости , но если вы действительно привязаны к понятию наличия нескольких длинных параллельных операций, то просто переносите каждую из этих операций в блок и затем отправляйте эти блоки в одну из глобальных параллельных очередей. Они будут работать параллельно. Если то, что у вас есть, больше соответствует строкам «нескольких рабочих процессов», в которых каждый рабочий процесс представляет собой определенную цепочку операций, которая должна выполняться поочередно, но параллельно с другими рабочими процессами, затем создавайте последовательную очередь для каждого рабочего процесса и независимого последовательного очереди будут выполняться одновременно друг с другом. Все просто! GCD часто смущает людей, которые ожидают, что вещи будут более сложными, или исходят из классического фона с резьбой и пытаются сопоставить одну концепцию с другой. Не делайте этого, и вам будет намного легче. :)

Смежные вопросы