Они не одинаковы. Метод get свойств вызывается каждый раз, когда вы получаете к нему доступ. По умолчанию, когда вы создаете свойство, за ним будет скрытое поле, поэтому:
public static Task CompletedTaskB { get; set; }
фактически сгенерирует это за кадром:
private static Task _completedTaskB;
public static Task CompletedTaskB
{
get {
return _completedTaskB;
}
set {
_completedTaskB = value;
}
}
Когда вы назначите свойство = Task.CompletedTask, вы устанавливаете его начальное значение, которое эквивалентно:
_completedTaskB = Task.CompletedTask;
Когда вы затем обращаетесь к свойству, оно будет читать из частного поля.
Я заметил, что вы определяем это как только для чтения (только получатель, а не установщик), поэтому вы не сможете назначить переменную. Вместо этого вам придется использовать:
public static Task CompletedTaskA { get { return Task.CompletedTask; } }
Это будет возвращать Task.CompletedTask все время.
В общем, разница между:
{ get; set; } = "some string";
и
get {return "some string"; }
заключается в том, что первое является начальным присваиванием, тогда как последнее является методом, который вызывается при каждом обращении к свойству.