Question

La façon idiomatiques de commencer une nouvelle tâche effet secondaire seulement (c'est: une tâche qui ne retourne aucun résultat) en utilisant le TPL .NET 4.0 utilise l'API suivante:

Task Task.Factory.StartNew(Action<object>, object)   

Mais pourquoi ne pas la signature de cette API ressemble à ceci

Task Task.Factory.StartNew<T>(Action<T>, T) 

ou comme celui-ci

Task Task.Factory.StartNew<T>(T, Action<T>) 

Des raisons techniques ou pour une autre raison?

Était-ce utile?

La solution

Bon, maintenant que je comprends bien la question:)

Je crois qu'il est parce que cela est censé être un directe remplacement ThreadPool.QueueUserWorkItem. Je suis d'accord qu'il semble un peu bizarre ... mais si vous utilisez des expressions lambda de toute façon, il est probablement plus facile d'utiliser la version fait prendre un paramètre d'état (c.-à- Action au lieu de Action<object>) et juste saisir la valeur que vous êtes intéressé à l'avance. Il ne sert à rien si vous spécifiez la valeur et la fonction séparément: (

Autres conseils

D'après un message par Stephen Toub (MSFT), ils partent du principe que nous allons compter sur les fermetures pour transmettre des données d'état. Il y avait aussi une excuse à propos de l'ambiguïté de la signature. ( http: //social.msdn. microsoft.com/Forums/en/parallelextensions/thread/1988294c-de41-476a-a104-aa550b7409f5 )

Cependant, en se fondant sur les fermetures pour résoudre ce problème semble être un hack temporaire en attendant une meilleure solution. Il fonctionne, mais ce n'est pas une bonne solution à long terme. Il y a beaucoup de fois que spécifiant simplement une méthode déléguée que l'action serait l'approche la plus simple, mais cela signifie que nous devons utiliser vars globales ou nous sommes exclus du passage des paramètres d'état.

J'aime l'une des propositions de Hugo (de l'affichage du forum MS). Hugo a suggéré d'introduire un type TaskState, ce qui semble être une façon intelligente de contourner la question des génériques d'ambiguïté.

Appliqué à la Task.Factory.StartNew () la signature et le constructeur des tâches () en tant que tel:

  public Task<T>( Action<T> function, TaskState<T> state );
  public Task<T,TResult>( Func<T,TResult> function, TaskState<T> state );

ActionState serait un peu comme la classe Nullable - juste une simple enveloppe autour d'un élément de valeur. Dans la pratique, l'utilisation TaskState pourrait ressembler à ceci:

  var myTask = new Task( MyMethod, new TaskState( stateInfo ) );
  ...

  public void MyMethod( StateInfo stateInfo ) { ... }

La solution TaskState <> est pas parfait, mais il semble comme une solution beaucoup mieux que de se fier à la fermeture de la coulée de type.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top