ASYNCHRONOUS PROGRAMMING
In asynchronous programming in c sharp there are synchronous methods and asynchronous methods. Let’s try to understand first of all when to perform operations asynchronously and when not. In general we can say that we must resort to asynchronous operations when we have to access I/O peripherals such as reading from the disk or working with the network. Connecting and sending queries to a database is an asynchronous operation, reading a large text file, sending a request to a web service, sending an email are all asynchronous operations.
Conversely, there is no benefit when a method is CPU intensive and is already optimizing the current thread. For example, calculating the Greek PI figures, sorting objects in a List, resizing an image are all operations that make intensive use of the CPU and already keep the thread actively engaged. There are operations that do not intensively occupy the thread that remains waiting, for example when a query is sent to a database it is the database that works if the thread were to wait for the results from the database an inefficiency would be introduced, if instead we use asynchronous operations the thread can break free and serve other requests such as in a web application.
LE KEYWORD AWAIT AND ASYNC
To mark a method as asynchronous we need to use the await keyword before calling the asynchronous method. This keyword designates the operation as asynchronous so it is necessary to wait for its completion before the next await statement is processed. Together with await, the async keywords must be used in the method signature. Using the await keyword will make a thread available to do more work. A task is a class that serves to describe an asynchronous operation. If the method returns void then Task is used otherwise Task<T>. The advantages of asynchronous programming are especially noticeable in the context of WPF applications, since in these cases the calling thread is almost always that of the user interface. These are methods that last a long time and block the interface and therefore the application is no longer responsive. This does not happen in the case of asynchronous execution. Also in other areas, such as that of web applications, asynchronous development has immense advantages, because it allows in any case to free up a thread that can be exploited by the server to serve another request.
using System; using System.Collections.Generic; using System.IO; using System.Net; using System.Net.Http; using System.Threading.Tasks; namespace ProgrammazioneAsincrona { class Program { static async Task Main(string[] args) { int result = await DownloadAsync(); Console.WriteLine($"String lenght: {result}"); IndependentWork(); await ParallelMethod(); } //ASYNCHRONOUS METHOD private static async Task DownloadAsync() { /* Asynchronous method. Under normal conditions, we should somehow manage the callback on this object to retrieve the information taken from the network; thanks to the await keyword, however, the compiler itself takes care of injecting all the necessary code, and we can simply just fetch the result of the asynchronous execution. Thread does not get stuck.*/ Console.WriteLine("Async Download"); WebRequest client = HttpWebRequest.Create("https://www.google.com"); var response = client.GetResponse(); using(var reader = new StreamReader(response.GetResponseStream())) { var result = await reader.ReadToEndAsync(); return result.Length; } } //SYNCHRONOUS METHOD private static int Download() { /*--Synchronous method. Until the result is retrieved, the thread remains blocked and waiting.*/ Console.WriteLine("Download"); WebRequest client = HttpWebRequest.Create("https://www.google.com"); var response = client.GetResponse(); using(var reader = new StreamReader(response.GetResponseStream())) { var result = reader.ReadToEnd(); Console.WriteLine(result); return result.Length; } } private static void IndependentWork() => Console.WriteLine("Method IndependentWork()...."); private static async Task ParallelMethod() { /*In this case, we have avoided using await on every single call, by storing the instances of the Task & lt; string & gt; returned within the tasks list. The result is that the code flow is no longer interrupted to wait for results and operations are actually started in parallel. To then retrieve the results, we must wait for all asynchronous calls to complete, awaiting the class's WhenAny method, as shown in the code.*/ Console.WriteLine("Parallel operations"); HttpClient client = new HttpClient(); Task task1 = client.GetStringAsync("http://www.google.com"); Task task2 = client.GetStringAsync("http://www.bing.com"); Task task3 = client.GetStringAsync("http://www.yhaoo.com"); var tasks = new List { task1, task2, task3 }; while (tasks.Count > 0) { Task finishedTask = await Task.WhenAny(tasks); if (finishedTask == task1) { Console.WriteLine($"Google number of characters on the page: {task1.Result.Length}"); } else if (finishedTask == task2) { Console.WriteLine($"Bing number of characters on the page: {task2.Result.Length}"); } else if (finishedTask == task3) { Console.WriteLine($"Yhaoo number of characters on the page: {task3.Result.Length}"); } tasks.Remove(finishedTask); } } } }
INSIGHT
Asynchronous programming in C# is a technique that allows background operations to be performed without blocking the main application thread. This is especially useful for I/O operations, such as database calls, reads/writes to files, and network requests, which can be slow.
C# offers several features for implementing asynchronous programming. Here is an overview of some of the most common techniques:
1. Using async and await
The most common way to write asynchronous code in C# is to use the keywords async and await. Here is a basic example:
using System;
using System.Net.Http;
using System.Threading.Tasks;
class Program
{
static async Task Main(string[] args)
{
string url = “https://example.com“;
string content = await DownloadContentAsync(url);
Console.WriteLine(content);
}
static async Task<string> DownloadContentAsync(string url)
{
using (HttpClient client = new HttpClient())
{
return await client.GetStringAsync(url);
}
}
}
In this example, DownloadContentAsync is an asynchronous method that uses HttpClient to download the content of a web page. The await keyword causes the method to wait for the asynchronous operation to complete without blocking the main thread.
2. Task Parallel Library (TPL).
The TPL is a library that provides a set of types and methods for performing tasks in parallel. Here is a basic example:
using System;
using System.Threading.Tasks;
class Program
{
static void Main(string[] args)
{
Task.Run(() => DoWork());
Console.WriteLine(“Work started“);
Console.ReadLine();
}
static void DoWork()
{
Task.Delay(2000).Wait(); // Simula un lavoro che richiede tempo
Console.WriteLine(“Work completed“);
}
}
3. Perform multiple operations in parallel
You can perform multiple asynchronous operations in parallel using Task.WhenAll or Task.WhenAny.
using System;
using System.Threading.Tasks;
class Program
{
static async Task Main(string[] args)
{
Task task1 = Task.Delay(2000);
Task task2 = Task.Delay(3000);
await Task.WhenAll(task1, task2);
Console.WriteLine(“Both tasks completed“);
}
}
Leave A Comment