Pergunta

Eu sei que existem várias maneiras de limitar o tempo de execução de uma tarefa no .Net e me perguntei se há outras que perdi ou modificações/melhorias nos métodos que usei anteriormente.

Onde não tenho certeza de como exatamente uma metodologia funciona, incluí perguntas sobre ela.

Métodos existentes que conheço, embora não necessariamente usados:

  1. Criar uma Thread, pesquise para que ele termine por um certo tempo e depois elimine o tópico.Esta solução não é ótima, pois depende de ThreadAbortExceptionsão um tanto desagradáveis ​​​​e, se bem me lembro, você não tem garantia de onde o código sairá, ou seja,pode deixar recursos não gerenciados em uso, etc.
  2. Use o IAsyncResult padrão, o problema com isso é que você pode esperar um certo período de tempo, mas não há uma maneira simples de sinalizar que deseja que a solicitação seja abortada, então você precisa confiar na configuração de um sinalizador booleano (ou similar) que é verificado dentro do código assíncrono e faz com que ele pare.O problema aqui é que, se o código assíncrono estiver preso em uma determinada seção do código, ele poderá continuar em execução por algum tempo antes de realmente terminar.
  3. Muitas vezes vi pessoas recomendando BackgroundWorker para coisas assíncronas, mas você pode usar isso no ASP.Net (presumo que sim) e ele tem uma maneira simples de encerrar o processo assíncrono após um certo tempo?
  4. Use a API de tarefas no .Net 4.0 (atualmente todo o meu trabalho está restrito ao .Net 3.5, portanto não é uma opção para mim).A partir de uma leitura rápida da documentação do MSDN, parece que você pode cancelar facilmente uma tarefa usando o CancellationToken mas com que rapidez um cancelamento entra em vigor e garante qualquer finally blocos são chamados.

Todas as soluções/sugestões/metodologias são bem-vindas

Foi útil?

Solução

A forma mais segura de cancelamento é sempre cooperativa.

Eu recomendo nunca matar um tópico (via ThreadAbortException).Se você não tiver escolha, faça desse código um código separado processo em vez disso, que pode ser morto de forma limpa.AppDomains foi uma boa ideia, mas não se compara ao mundo real.

IAsyncResult, BackgroundWorker, e CancellationToken são todas formas de cancelamento cooperativo.Então eles estão todos muito limpos (sem perder recursos, ligando finally blocos, ...), mas têm a desvantagem de não poderem lidar com código "não autorizado".

Se você estiver escrevendo o código da tarefa em segundo plano, basta usar BackgroundWorker ou CancellationToken.Se você precisar trabalhar com código possivelmente "não autorizado", envolva-o em um processo separado.

BackgroundWorker funcionará perfeitamente no ASP.NET e apoia o cancelamento cooperativo.

Outras dicas

O token de cancelamento de 4 e o sinalizador booleano de 2 são o mesmo tipo de mecanismo.Em ambos os casos a tarefa tem de cooperar e verificar a bandeira regularmente.A vantagem do 4 é que você tem uma bandeira padronizada em vez de criar a sua própria.

Abortar threads é ruim, mas administrável se seu código for escrito com cuidado.Em particular, é fácil corromper o estado global.

A versão segura de anular um thread é executá-lo em um domínio de aplicativo diferente.Em seguida, você descarrega o domínio do aplicativo assim que o thread for eliminado.Isso funcionará de maneira segura se todos os seus recursos não gerenciados tiverem finalizadores críticos corretos/usar SafeHandles.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top