首页 > 解决方案 > Typescript 中的运行时属性

问题描述

我正在定义一个需要在运行时计算属性以避免冗余的对象。例如 :

export class Assessment {
    items: Question[];
    time?: number; // optional property
    scoreTotal?: number; // runtime computed property (sum of questions scores)
}

export class Question {
    score: number;
    statement: string;
    responses: string[];
    correctResponse: string;
}

scoreTotal?有效,但它可能会产生误导(人们可能认为它是可选的)。

还有另一种方法吗?

编辑:我希望避免使用方法,因为我多次阅读此属性。我想设置一次。

标签: typescriptclasspropertiesoptional

解决方案


分为Assessment2种;有和没有scoreTotal. 您可以使用“标记联合”类型最优雅地做到这一点。

interface AssessmentBase {
    items: Question[];
    time?: number; // optional property
}

interface AssessmentWithoutScoreTotal extends AssessmentBase {
    type: "AssessmentWithoutScoreTotal",
}

interface AssessmentWithScoreTotal extends AssessmentBase {
    type: "AssessmentWithScoreTotal",
    scoreTotal: number; // runtime computed property (sum of questions scores)
}

type Assessment = AssessmentWithoutScoreTotal
    & AssessmentWithScoreTotal;

当然,Assessment将不再是一个类。但是您可以根据自己的需要制作AssessmentWithoutScoreTotal或成为课程。AssessmentWithScoreTotal但是,它真的必须是一个类吗?我发现普通接口在大多数情况下工作得更好。

尽管如此,您必须小心items在计算 之后不要更改属性totalScore,因此键入它也可能有意义:

interface Question {
    readonly score: number;
    statement: string;
    responses: string[];
    correctResponse: string;
}

interface AssessmentBase {
    time?: number; // optional property
}

interface AssessmentWithoutScoreTotal extends AssessmentBase {
    type: "AssessmentWithoutScoreTotal",
    items: Question[];
}

interface AssessmentWithScoreTotal extends AssessmentBase {
    type: "AssessmentWithScoreTotal",
    scoreTotal: number; // runtime computed property (sum of questions scores)
    readonly items: readonly Question[]; // Shouldn't mutate the scores anymore, since total has been precomputed.
}

type Assessment = AssessmentWithoutScoreTotal
    & AssessmentWithScoreTotal;

推荐阅读