Как инициализировать объект, используя шаблон async-await

я пытаюсь следовать шаблону RAII в моих классах обслуживания, что означает, что когда объект создается, он полностью инициализируется. Однако я'Я сталкиваюсь с трудностями с асинхронными API. Структура рассматриваемого класса выглядит следующим образом:

class ServiceProvider : IServiceProvider // Is only used through this interface
{
    public int ImportantValue { get; set; }
    public event EventHandler ImportantValueUpdated;

    public ServiceProvider(IDependency1 dep1, IDependency2 dep2)
    {
        // IDependency1 provide an input value to calculate ImportantValue
        // IDependency2 provide an async algorithm to calculate ImportantValue
    }
}

м также нацелена на избавление от побочных эффектов вImportantValue getter, чтобы сделать его потокобезопасным.

Сейчас пользователиServiceProvider создаст его экземпляр, подпишется на событиеImportantValue изменить и получить начальныйImportantValue, И тут возникает проблема с начальным значением. ПосколькуImportantValue вычисляется асинхронно, класс не может быть полностью инициализирован в конструкторе. Вполне возможно, что изначально это значение будет равно нулю, но тогда мне нужно найти место, где оно будет вычислено в первый раз. Естественным местом для этого может бытьImportantValueполучатель, но яm таргетинг, чтобы сделать его потокобезопасным и без побочных эффектов.

Так что я'Я в основном застрял с этими противоречиями. Не могли бы вы помочь мне и предложить альтернативу? Инициализация значения в конструкторе, в то время как nice не является действительно необходимой, но никакие побочные эффекты и потокобезопасность свойства не являются обязательными.

Заранее спасибо.

РЕДАКТИРОВАТЬ: Еще одна вещь, чтобы добавить. Я'Я использую Ninject для создания экземпляров, и, насколько я понимаю, это не• Поддержка асинхронных методов для создания привязки. Хотя подход с инициированием какой-либо операции на основе задач в конструкторе будет работать, я не могу дождаться ее результата.

То есть два следующих подхода (предложенные в качестве ответов) не скомпилируются, поскольку возвращается Task, а не мой объект:

Kernel.Bind().ToMethod(async ctx => await ServiceProvider.CreateAsync())

или же

Kernel.Bind().ToMethod(async ctx => 
{
    var sp = new ServiceProvider();
    await sp.InitializeAsync();
})

Простое связывание будет работать, но яя не ожидаю результата асинхронной инициализации, запущенной в конструкторе, как предложил Стивен Клири:

Kernel.Bind().To();

... и этоне выглядит хорошо для меня.

Ответы на вопрос(5)

Ваш ответ на вопрос