Подтвердить что ты не робот

Многопоточность в IronPython

У меня есть класс "script" в IronPython, а скриптинг в моем приложении работает, вызывая методы на его экземпляре. Мне нужно реализовать сценарии вызова из нескольких потоков. Каков правильный способ сделать это?

У меня много проблем:

В целом: как правильно реализовать запуск того же script для разных аргументов в нескольких потоках? Скрипты должны выполняться одновременно и не должны вылетать из-за условий гонки.

4b9b3361

Ответ 1

1.

Если документация ScriptScope говорит, что она не является потокобезопасной, верьте ей или, по крайней мере, действуйте так, как вы ей верите. @JimmySchementi, возможно, рассмотрела текущую реализацию и выяснила, что она в настоящее время является потокобезопасной, но это не дает никаких гарантий того, как она будет вести себя в следующем патче класса, не говоря уже о следующем крупном выпуске.

2.

Да, вам нужно будет инициализировать каждый из ваших ScriptScopes. Я попытался бы свести к минимуму количество требуемых ScriptScopes, как это сделать будет зависеть от вашей настройки. Если основной целью соответствующих потоков является размещение ScriptScope, тогда вы должны использовать ThreadPool с каждым потоком, имеющим один ThreadLocal <ScriptScope> . Если эти потоки выполняют другие действия, а также запущенные скрипты, тогда у вас должен быть пул объектов, в котором хранятся ScriptScopes, и каждый поток может проверить ScriptScopes, выполнить работу, а затем освободить ScriptScope.

3.

Предпочитайте ThreadLocal через ThreadStatic, если вы идете по этому пути.

Ответ 2

Вот как вы это делаете в сценариях, если я правильно вас понял.

https://github.com/dretax/Python-Plugins/blob/master/PlutonPlugins/PluIRC/PluIRC.py#L154

Посмотрите, что делает этот script, он полностью запускает новый поток одной и той же вещи с разными аргументами.

Файл py, который вы можете увидеть, если FULLY threaded, и использует IronPython. Это КАК вы правильно делаете потоки, а НЕ каким-либо другим способом.

Ответ 3

Так как это не похоже на то, что вы получаете конкретный ответ, у меня общий.

Один мой коллега использовал IronPhython в моей предыдущей работе и обработке многопоточности было бы очень важно, поэтому я могу сказать, что можно запустить IronPython в многопоточной среде на производственной системе.

Я не знаю, использовал ли он свою собственную блокировку или зависел от блокировки внутри IronPython.

Я бы предложил:

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

    [Test]
    public void TwoThreadsWithTheirOwnContexts() {
        //Create two threads
        var tasks = new Task[2];
        tasks[0] = Task.Factory.StartNew(PrintSomethingInIronPython1);
        tasks[1] = Task.Factory.StartNew(PrintSomethingInIronPython2);
        Task.WaitAll(tasks);
    }

b) В любом случае добавьте блокировки. Возможно, не большая проблема с блокировкой в ​​коде, и вы устраните неопределенность.

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

Re 2: Опять предложение. Создайте потоки пулов, которые инициализируют один раз, а затем повторно используют эти потоки.