Огонь и забудь, что не запланировано - PullRequest
0 голосов
/ 24 мая 2018

Я использую Task.Run (() => this.someMethod ()), чтобы запланировать фоновое задание.Меня не интересует результат операции, и мне нужно продолжать работу с потоком приложения.

Но иногда моя фоновая задача не может быть запланирована на долгое время. Это начало происходить с тех пор, как мы перешли из .Net4.7 из 4.5.Даже при отладке точки останова либо не достигаются, либо удаляются после значительной задержки (> 10 минут).

Кто-нибудь заметил это поведение или знает, что его вызывает?

Я работаю на ядре i7, 16 ГБ ОЗУ.

Ответы [ 2 ]

0 голосов
/ 26 мая 2018

Я не знаю, сколько задач вы запускаете таким образом, но если их число не будет действительно высоким, я бы сосредоточил отладку на вызываемом методе, а не на вызывающем.Задержка в 10 минут более вероятна из-за тупика или проблемы с сетью, чем из-за планирования задач.

Некоторые идеи:

  1. Для начала я бы добавил что-то в начало иконец вызываемого метода, который позволяет узнать, когда он начинает выполняться и когда он заканчивается.Как и Debug.WriteLine () с отметкой времени и идентификатором задачи.
  2. Убедитесь, что вызываемый метод освобождает все ресурсы, даже если происходит сбой.Сбои потоков / задач могут остаться незамеченными, потому что они не вызывают сбой приложения.
  3. Дважды проверьте, что вызываемый метод является потокобезопасным.Возможно, в прошлом вам повезло, и некоторая новая оптимизация фреймворка сейчас вызывает хаос.
0 голосов
/ 24 мая 2018

Если ваша задача занимает 10 минут, чтобы даже начать звучать подозрительно.Я предполагаю, что ваша система находится под большой нагрузкой или у вас запущено много задач.

Я собираюсь атаковать позже (для конкретной ситуации).

TaskCreationOptions

LongRunning Указывает, что задача будет длительной, крупнозернистой операцией, включающей меньшее количество компонентов большего размера, чем мелкозернистых систем.Он дает подсказку TaskScheduler, что переподписка может быть оправдана.Oversubscription позволяет создавать больше потоков, чем доступное количество аппаратных потоков.Он также дает подсказку планировщику задач о том, что для этой задачи может потребоваться дополнительный поток, чтобы он не блокировал продвижение вперед других потоков или рабочих элементов в локальной очереди пула потоков.

var task = new Task(() => MyLongRunningMethod(),TaskCreationOptions.LongRunning);
task.Start();

Это цитата Стивена Туба - MSFT в этом сообщении

Под обложками это приведет к большему количествуиспользуемые потоки, поскольку его цель - позволить ThreadPool продолжать обрабатывать рабочие элементы, даже если одна задача выполняется в течение продолжительного периода времени;если бы эта задача выполнялась в потоке из пула, этот поток не смог бы обслуживать другие задачи.Обычно вы используете LongRunning только в том случае, если в ходе тестирования производительности вы обнаружили, что неиспользование его приводит к длительным задержкам при обработке другой работы.

Трудно понять, в чем заключается ваша проблема, если вообще не смотретьВаш код, однако я разместил это как предложение.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...