Многопоточный поиск пополам

Предположим, что у меня есть некоторый вычислимый предикат, P, который отображает целые числа в bools. я знаю это P 0 это правда, и я знаю, что некоторые N, что P N ложно Я тоже знаю что P n = false подразумевает, что P (n + 1) is false [*]. Я хочу найти максимальное такое, что P n правда.

Ясно, что я могу найти решение этой проблемы путем деления пополам. К сожалению, оценка P стоит дорого (возможно, это займет час или около того). У меня также есть блестящий сервер со многими ядрами.

Если оценка P заняла постоянное время и у меня было 2 потока (скажем), я вижу, как я буду выполнять поиск. Я бы разделил интервал [a, b] на три сегмента и оценил бы P (2a + b)/3 а также P (a + 2b)/3, После того, как обе оценки будут завершены, я буду знать, в какой из трех сегментов перейти. Используя две темы, мое время поиска будет сокращено на треть. Отлично!

Тем не менее, что, если оценка P занимает чрезвычайно разное время? В моем конкретном примере это может занять от 10 секунд до часа или около того. Предположим еще раз, что у меня есть 2 потока и я разделил интервал, как указано выше. Может быть, первая тема (оценка P (2a+b)/3) заканчивает первым. Как мне решить, где запустить следующий?

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

[*] В конкретном случае, который меня волнует, тест включает запуск решателя SMT, пытающегося найти решение X для задачи с ограничением с одним дополнительным ограничением в форме X ≥ n, где n - целое число выше.

2 ответа

Решение

Если вы ищете справку на бумаге, вы можете получить больше тяги на CS.SE. Здесь я могу предложить только некоторые эвристики.

Всякий раз, когда поток завершается, вы можете остановить все другие потоки, чей ответ вы теперь знаете (например, если вы получили P(n)=T, вы можете остановить все темы, работающие на k<n, и если P(n)=F, вы можете остановить все темы, работающие на k>n). Таким образом, теперь у вас есть 1 или более потоков для запуска.

Из теоретико-информационного POV деление существующих интервалов для минимизации максимальной длины новых интервалов является, очевидно, оптимальным.

Однако, так как вы заметили в комментарии:

SMT решатель занимает гораздо больше времени для удовлетворительных решений

Это может быть быстрее начать с большой n и идти вниз медленно (например, если вы знаете, что P(100)=F а также P(1)=T, протестируйте 95, 90, 80 в 3 потока, вместо 25, 50, 75, как рекомендовано теорией информации).

Вы также можете использовать время выполнения в качестве индикатора вероятного результата. Например, начните свои 3 темы в n=25,50,75, Предположим, что за 1 минуту вы узнаете P(75)=F но два других все еще работают. Тогда вы можете положить n=25 поток для сна (чтобы быть пробужденным или убитым в будущем по мере необходимости) и запустить два новых потока для 60 и 70.

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

Я бы попробовал стратегию, которая является бинарным поиском, который начинает больше оценок на половине интервала Например, если необходимо проверить интервал [0, 100] и существует 8 потоков, чем начальные оценки для n=[47, ..., 54]. Когда первая оценка закончится, убейте оценки, которые не могут быть результатом, приостановите другие оценки и продолжайте ~ половину предыдущего интервала. Когда интервал немного больше, чем число потоков (~1,5x), используйте некоторую стратегию, чтобы покрыть весь интервал оценками, так как, чтобы найти результат, вы должны проверить обоих соседей. Не будет более 2*num_threads приостановленных оценок.

Другие вопросы по тегам