await Console.ReadLine()

11,355

I know that threads are an expensive resource so I feel really wasteful and hacky doing this. I also tried Console.In.ReadLineAsync() but it is apparently buggy? (It seems to hang).

The console streams unfortunately do have surprising behavior. The underlying reason is that they block to ensure thread safety for the console streams. Personally I think that blocking in an asynchronous method is a poor design choice, but Microsoft decided to do this (only for console streams) and have stuck by their decision.

So, this API design forces you to use background threads (e.g., Task.Run) if you do want to read truly asynchronously. This is not a pattern you should normally use, but in this case (console streams) it is an acceptable hack to work around their API.

However, my (limited) understanding is that calling Task.Run will fire off a new (parallel?) thread.

Not quite. Task.Run will queue some work to the thread pool, which will have one of its threads execute the code. The thread pool manages the creation of threads as necessary, and you usually don't have to worry about it. So, Task.Run is not as wasteful as actually creating a new thread every time.

Share:
11,355
Stephen Foster
Author by

Stephen Foster

Updated on June 13, 2022

Comments

  • Stephen Foster
    Stephen Foster almost 2 years

    I am currently building an asynchronous console application in which I have created classes to handle separate areas of the application.

    I have created an InputHandler class which I envisioned would await Console.ReadLine() input. However, you cannot await such a function (since it is not async), my current solution is to simply:

    private async Task<string> GetInputAsync() {
        return Task.Run(() => Console.ReadLine())
    }
    

    which runs perfectly fine. However, my (limited) understanding is that calling Task.Run will fire off a new (parallel?) thread. This defeats the purpose of async methods since that new thread is now being blocked until Readline() returns right?

    I know that threads are an expensive resource so I feel really wasteful and hacky doing this. I also tried Console.In.ReadLineAsync() but it is apparently buggy? (It seems to hang).