ค้นหาเว็บไซต์

Typescript - ฉันจะได้อาร์เรย์ที่มีชนิดกำหนดได้อย่างไร?


กรณีตัวอย่างการใช้งานของฉัน

type someEnum = 'a' | 'b';

const someObj: { [K in someEnum]: string } = {
    a: 'a',
    b: 'b',
};

const a: Array<someEnum> = ['a', 'b'];

// In Future update someEnum

type someEnum = 'a' | 'b' | 'c';

// Gives an error;

// Property 'c' is missing in type '{ a: string; b: string; }' 
// but required in type '{ a: string; b: string; c: string; }'.

const someObj: { [K in someEnum]: string } = {
    a: 'a',
    b: 'b',
};

// No error;
const a: Array<someEnum> = ['a', 'b'];

// Is There someThing like;

// const typedArray: [K in someEnum]

คงจะเจ๋งมากถ้ามีฟีเจอร์แบบนั้น; มีฟังก์ชันอะไรที่สามารถทำให้ได้เหมือนกันไหม ขอบคุณล่วงหน้า

คำตอบ #1

มันน่าล่อใจที่จะใช้วิธีแก้ปัญหาบางอย่างเพื่อเปลี่ยนทูเพิลเป็นยูเนียน กรุณาอย่าใช้มัน

คุณสามารถแก้ไขปัญหานี้ได้หลายวิธี วิธีที่ง่ายที่สุดคือถ้า enum อยู่ภายใต้การควบคุมของคุณ ให้เริ่มจาก array แทนที่จะเป็น enum:

const allPosibilitieForSomeEnum = ['a',  'b' , 'c'] as const
type someEnum = typeof allPosibilitieForSomeEnum[number];

คุณสามารถใช้วัตถุแทนและใช้ keys เพื่อรับกุญแจได้

หรือคุณสามารถใช้ฟังก์ชันที่ตรวจสอบว่ามีสมาชิกทั้งหมดครบถ้วน:

type someEnum = 'a' | 'b' | "c";

function checkEnum<TEnum>() {
    return function <TActual extends TEnum[]>(...p: TActual & ([TEnum] extends [TActual[number]] ? {} : {
        error: ["Array does not contain all members, expected: ", TEnum, "found:", TActual[number]]
    })) {
        return p
    }
}

const someObj =  checkEnum<someEnum>()("a", "b", "c") 
const someObj2 =  checkEnum<someEnum>()("a", "b") ///  Property 'error' is missing in type '["a", "b"]' but required in type '{ error: ["Array does not contain all members, expected: ", someEnum, "found:", "a" | "b"]; }'.

คำตอบ #2

คุณต้องการสร้างทูเพิลจากประเภทยูเนียน ซึ่งเป็นไปได้จริงแต่ซับซ้อนเล็กน้อย นอกจากนี้ยังมีปัญหาในที่เก็บ GitHub ของ TypeScript ที่กล่าวถึงเรื่องนี้ด้วย

หนึ่งในคำตอบที่นั่นดูเหมือนจะใช้ได้ดีมาก นี่คือตัวอย่างใน TypeScript Playground