Введите класс защиты в операторе переключения

Я не использую Typescript уже много лет и не могу вспомнить и найти, как правильно вводить многие классы внутри оператора переключателя.

class A {}
class B {}
class C {}

type OneOfThem = A | B | C;

function test(foo: OneOfThem): string {
    switch(/* something using foo */) {
        /* A */:
            return "A";
        /* B */:
            return "B";
        /* C */:
            return "C";

        /* should not need to use "default" as all cases are handled */
    }
}

Я нашел и попробовал несколько вариантов, например:

но ни один из них не работает (Function lacks ending return statement and return type does not include 'undefined').

Может быть, моя память подводит, и на занятиях это невозможно?

Вы можете выдать ошибку в случае по умолчанию, чтобы удовлетворить исчерпывающую диагностику соответствия шаблону (пример ).

jsejcksn 28.04.2024 14:28

Если я это сделаю, средство проверки типов не предупредит меня об отсутствующем регистре, но столкнется с ошибкой во время выполнения, которую я использую машинописный текст, чтобы избежать ее, насколько это возможно.

Ettapp 30.04.2024 04:58
Зод: сила проверки и преобразования данных
Зод: сила проверки и преобразования данных
Сегодня я хочу познакомить вас с библиотекой Zod и раскрыть некоторые ее особенности, например, возможности валидации и трансформации данных, а также...
Как заставить Remix работать с Mantine и Cloudflare Pages/Workers
Как заставить Remix работать с Mantine и Cloudflare Pages/Workers
Мне нравится библиотека Mantine Component , но заставить ее работать без проблем с Remix бывает непросто.
Угловой продивер
Угловой продивер
Оригинал этой статьи на турецком языке. ChatGPT используется только для перевода на английский язык.
TypeScript против JavaScript
TypeScript против JavaScript
TypeScript vs JavaScript - в чем различия и какой из них выбрать?
Синхронизация localStorage в масштабах всего приложения с помощью пользовательского реактивного хука useLocalStorage
Синхронизация localStorage в масштабах всего приложения с помощью пользовательского реактивного хука useLocalStorage
Не все нужно хранить на стороне сервера. Иногда все, что вам нужно, это постоянное хранилище на стороне клиента для хранения уникальных для клиента...
Что такое ленивая загрузка в Angular и как ее применять
Что такое ленивая загрузка в Angular и как ее применять
Ленивая загрузка - это техника, используемая в Angular для повышения производительности приложения путем загрузки модулей только тогда, когда они...
1
2
57
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

добавление дополнительного члена к трем классам, которые будут использоваться в операторе переключения

Это действительно, вероятно, самое простое решение для вашего случая: он использует Дискриминируемый союз , добавляя дискриминантный член в каждый класс с литеральными типами (т. е. не только string или number), так что вы (и TypeScript) могу отличить foo из какого класса:

class A {
    readonly kind = "a"
    //       ^? "a" string literal, not just `string`
}
class B {
    kind: "b" = "b"
    // ^? "b" string literal, as explicitly typed
}
class C {
    kind = "c" as const
    // ^? "c" string literal, thanks to the const assertion
}

Затем просто дифференцируйте на основе этого kind дискриминантного свойства:

function test(foo: OneOfThem): string { // Okay
    switch (foo.kind) {
        case "a":
            foo
            //^? A inferred by TS, based on `foo.kind === "a"` type guard
            return "A";
        case "b":
            foo
            //^? B
            return "B";
        case "c":
            foo
            //^? C
            return "C";
        /* should not need to use "default" as all cases are handled */
    }
}

Ссылка на игровую площадку

readonly все получилось, спасибо!
Ettapp 28.04.2024 04:11

Действительно, если быть точным, вам просто нужно убедиться, что свойство дискриминанта имеет буквальные значения типа (т. е. не просто string): tsplay.dev/wXL79w В ответе я сделаю это более подробно.

ghybs 28.04.2024 07:11

Другие вопросы по теме