Подтвердить что ты не робот

Почему прерывание требуется после возврата доходности в инструкции switch?

Может ли кто-нибудь сказать мне, почему компилятор считает, что break необходим после yield return в следующем коде?

foreach (DesignerNode node in nodeProvider.GetNodes(span, node => node.NodeType != NDjango.Interfaces.NodeType.ParsingContext))
{
    switch (node.ErrorMessage.Severity)
    {
        case -1:
        case 0:
            continue;
        case 1:
            yield return new TagSpan<ErrorTag>(node.SnapshotSpan, new ErrorTag(PredefinedErrorTypeNames.Warning));
            break;
        default:
            yield return new TagSpan<ErrorTag>(node.SnapshotSpan, new ErrorTag(PredefinedErrorTypeNames.SyntaxError));
            break;
    }
}
4b9b3361

Ответ 1

Потому что возврат доходности - это просто синтаксический сахар для генератора итератора, и вы фактически не покидаете какой-либо метод. И С# не разрешает провал в switch (и это не похоже, что вы все равно хотите его здесь).

Ответ 2

Почему прерывание требуется после возврата в инструкции switch?

Вопрос предполагает неправильную предпосылку. Оператор break не требуется после возврата доходности в инструкции switch. Например:

switch(x)
{
case 123:
    yield return 456;
    M();
    throw new Exception();
case 789: // and so on

Здесь у нас есть доходность возврата в инструкции switch, за которой не следует разрыв. Затем следует вызов M(), а затем оператор throw. Это совершенно законно.

Реальное правило заключается в том, что конечная точка секции переключения не должна достижима.

Конечные точки разрыва, continue, return, goto, return и throw недоступны, потому что все эти утверждения выходят в другое место и не возвращаются, так что токен кода, следующий за ними, недоступен. Это контрастирует, например, с вызовом метода, который переходит в другое место, а затем возвращается или возвращает доход, который передает управление обратно вызывающему абоненту; когда вызывающий абонент передает управление обратно в блок итератора, элемент управления будет выбирать, где возврат возврата оставлен, поэтому конечная точка возврата доходности достижима.

Если этот вопрос вас интересует, я рекомендую прочитать раздел 8.1 спецификации.

Ответ 3

"Нормальный" возврат имеет две функции:

  • Отметьте возвращаемое значение функции.
  • Управление передачей вызывающему.

Возврат ýield возвращает только возвращаемое значение; это не влияет на поток управления. После утверждения возврата доход выполнение программы продолжается на следующей строке, где в вашем примере требуется разрыв, как и в любом другом случае с switch-case.