LuaEden X
LuaEden X

Reputation: 21

Wait till string is not null, then proceed with the code

I have a public string called simply m. The code shall only proceed when m is not null anymore. As long as m is null it should just wait. Any suggestions on how to do that? ( Without pausing the entire program, otherwise m would never change)

Upvotes: 1

Views: 4470

Answers (5)

zivkan
zivkan

Reputation: 14991

You can use a TaskCompletionSource<TResult>.

Create a new instance, and anywhere that needs to wait for the string to be available, you can use await tcs.Task. When whatever produces the string finishes, you call tcs.SetResult(result).

This allows your code to avoid busy-loops, as one other answer suggested, and if you have a highly concurrent application, it avoids blocking threads, as another answer suggested.

Upvotes: 5

Johan Donne
Johan Donne

Reputation: 3285

If you are looking for a simple async solution with a small latency:

await Task.Run(async () => { while (string.IsNullOrWhiteSpace(m)) await Task.Delay(10); });

or

while (string.IsNullOrWhiteSpace(m)) await Task.Delay(10);

Upvotes: 3

V0ldek
V0ldek

Reputation: 10563

I am assuming we're talking about a multi-threaded environment. Refer to Condition Variables in C#/.NET. You can use the Monitor class, but you need to change your public field to a property (which you should do anyway).

private readonly string? _m;

public string? M
{
    get => _m;
    set
    {
        lock (_m)
        {
            _m = value;
            if (_m != null)
            {
                Monitor.PulseAll(_m);
            }
        }
    }
}

public void Foo()
{
    lock (_m)
    {
        while (_m == null)
        {
            Monitor.Enter(_m);
        }

        // Code using the _m resource...
    }

    // Rest of your code...
}

This will work and is enough if you have a small number of threads and locking will be rather rare. If there are multiple threads reading from and writing to _m, this might be unperformant and you might want to mix this with a ReaderWriterLockSlim](https://learn.microsoft.com/en-us/dotnet/api/system.threading.readerwriterlockslim?view=netstandard-2.1) to optimise for the common case of _m not being null.

Upvotes: 0

Coding Enthusiast
Coding Enthusiast

Reputation: 159

How about turning your "public string" into a property?

private string _m
public string M
{
    get => _m;
    set 
    {
        if (value != _m)
        {
            _m = value;
            if (string.IsNullOrEmpty(value))
            {
                DoSomething(value);
            }
        }
    }
}

Upvotes: 2

Shreyash Solanke
Shreyash Solanke

Reputation: 381

The simplest solution in this case is write a while(true) loop and add if statement which checks string is null or not. But this will keep consuming CPU cycles unnecessarily. So I suggest you to implement conditional wait which will basically trigger your code once the condition is matched (string becomes null in your case) and will not waste CPU cycles in just waiting.

Upvotes: 0

Related Questions