.NET 4.0 ha il TPL che contiene la bella classe Task per incapsulare i modelli di programmazione asincrona. Sto lavorando su un'app che deve essere .NET 2.0, ma voglio evitare di riscrivere Task. Eventuali suggerimenti?Cosa devo fare per utilizzare l'attività <T> in .NET 2.0?
risposta
So che hai detto che non vuoi riscrivere compito, ma puoi effettivamente creare qualcosa di abbastanza semplice usando le chiusure, che si comporta in qualche modo come un oggetto Task. Questo è quello che io uso:.
public delegate R AsyncTask<R>();
public static AsyncTask<R> BeginTask<R>(AsyncTask<R> function)
{
R retv = default(R);
bool completed = false;
object sync = new object();
IAsyncResult asyncResult = function.BeginInvoke(
iAsyncResult =>
{
lock (sync)
{
completed = true;
retv = function.EndInvoke(iAsyncResult);
Monitor.Pulse(sync);
}
}, null);
return delegate
{
lock (sync)
{
if (!completed)
{
Monitor.Wait(sync);
}
return retv;
}
};
}
sua una funzione che chiama BeginInvoke() sul delegato si passa, e restituisce una funzione che quando viene chiamato blocca e attende il risultato della funzione passata in Faresti devono creare sovraccarichi di questa funzione per diverse firme di metodo, ovviamente.
Un modo per andare, è possibile adattarlo alle proprie esigenze e aggiungere altri comportamenti come Continuazioni, ecc. La chiave è usare chiusure e delegati anonimi. Dovrebbe funzionare in .NET 2.0.
EDIT - Ecco come si dovrebbe utilizzare:
public static string HelloWorld()
{
return "Hello World!";
}
static void Main(string[] args)
{
var task = BeginTask(HelloWorld); // non-blocking call
string result = task(); // block and wait
}
Si dovrà usare System.Threading.Thread
classe, è possibile ottenere la classe Task
per .NET 3.5, ma non per .net 2.
spiacenti
ho avuto l'impressione che la classe Task è dotato di .NET 4. Come potrei usarlo sotto 3.5? –
Il team [Rx] (http://go.microsoft.com/fwlink/?LinkID=179929) ha eseguito il backport di 'Task' e altre astrazioni di basso livello (ma non dell'intera TPL) in .NET 3.5 SP1. –
@Christial Schwarz, ^^ come ha detto Stephen, è stato backported. – Jethro
Grazie Sean. Questo è un buon punto di partenza. –
Per chiunque attraversi il codice, nota BeginInvoke come usato in precedenza avvia HelloWorld su [un nuovo thread dal pool di thread gestito] (http://stackoverflow.com/questions/3556634/does-funct-begininvoke-use-the-threadpool). – rkagerer