Поддержание отзывчивости пользовательского интерфейса в C # или C / CLI

#c# #c #.net #multithreading #asynchronous

#c# #c #.net #многопоточность #асинхронный

Вопрос:

Это несколько общий вопрос, поскольку я читал учебные пособия / пошаговые руководства по MSDN C #. Я также просмотрел здесь несколько сообщений, но хотел получить более общий ответ.

Я только что прочитал раздел асинхронного программирования, и кажется, что использование async, await и tasks является одним из предлагаемых способов запуска при сохранении отзывчивости пользовательского интерфейса.

Я пишу программу на C # для управления роботом для выполнения определенных задач. Например, программа будет иметь основной пользовательский интерфейс, который пользователь настраивает, затем, когда он нажмет «ВЫПОЛНИТЬ», он выполнит последовательность задач, а затем завершит. Если я не использую асинхронное или параллельное программирование, пользовательский интерфейс будет зависать до завершения.

Мой вопрос в том, каков типичный способ обработки этих ситуаций? Основываясь на том, что я прочитал, я могу сделать следующее на C#:

  1. Сделайте обработчик нажатия кнопки «ВЫПОЛНИТЬ» асинхронным, чтобы я мог ожидать выполнения задач
  2. Запускайте каждую из моих синхронных операций как задачу и ожидайте их завершения в обработчике «ВЫПОЛНИТЬ», например:

    Task t = synchronousMethod1();
    await t;
    t = synchronousMethod2();
    await t;
    repeat...

Это лучший способ сделать это? Если вы представляете, что мне нужно выполнить много движений робота, мне пришлось бы создавать множество задач для выполнения каждого движения при сохранении отзывчивости пользовательского интерфейса. Однако каждая задача будет иметь минимальные требования к вычислениям и будет выполняться довольно быстро, но я не уверен, является ли это хорошей практикой или нет.

Кроме того, из любопытства, каков стандартный способ сделать это на C ?

Комментарии:

1. ну, вам также следует взглянуть на BackgroundWorker . В вашем случае кажется, что ваши задачи / действия должны выполняться друг за другом, поэтому лучше использовать фоновый рабочий, поскольку он также очень легко сообщает о прогрессе

2. @Franck async/await также позволяет сообщать о ходе выполнения. BackgroundWorker в основном устарел и, как правило, не должен использоваться, если вместо него можно использовать async / await . Последний имеет много преимуществ, в том числе его проще тестировать

3. @leonhart88 я не уверен, что вы что-то выиграете, используя несколько задач, и вы можете попасть в сложные ситуации, которые будет сложно отладить. Предполагая, что каждое движение зависит от завершения предыдущего, тогда одна задача — это путь. Ваш пользовательский интерфейс будет отзывчивым, и вам будет гарантировано, что ваши движения будут выполняться в правильном порядке

4. @AvrohomYisroel Да, я также читал, что BackgroundWorker устарел. Хороший момент в том, что не нужно выполнять несколько задач. Возможно, мне придется разбить задачи или иметь вложенные задачи (это плохо?). Например, я могу сказать роботу перейти в позицию 1, изображение, позицию 2, изображение, позицию 3, изображение. После каждого изображения я хотел бы выполнить некоторую обработку. Я мог бы сделать все это последовательно в одной задаче, но если я могу перейти к позиции 1, изображению и создать задачу, Перейти к позиции 2, изображению и создать задачу и т. Д., А Затем дождаться всех этих задач, я чувствую, что это может быть более эффективным.

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