当前位置: 首页 > 知识库问答 >
问题:

如何在TypeScript中为类属性动态赋值

艾心远
2023-03-14

我想在TypeScript中动态地为MyClass分配多个属性,这样就不需要编写多行代码来设置类属性。我写了以下代码:

interface IMy
{
    visible?: boolean;
    text?: string;
}

class MyClass
{
    element: JQuery;

    assing(o: IMy): void
    {
        for (let [key, value] of Object.entries(o))
        {
            if (typeof value !== "undefined")
                this[key] = value;
        }
    }

    get visible(): boolean
    {
        return this.element.is(":visible");
    }

    set visible(visible: boolean)
    {
        this.element.css("display", visible ? "" : "none");
    }

    get text(): string
    {
        return this.element.html();
    }

    set text(text: string)
    {
        this.element.html(text);
    }
}

let t = new MyClass();
t.assign({ visible: true });
//instead t.visible = true;

//or

t.assign({ text: "Something" });
//instead t.text = "something";

//or

t.assign({ text: "Something", visible: false });
//instead t.visible = true; 
//        t.text = "something";

但是,我在第行的[key]=值中遇到了问题 有错误:

对象类型的索引签名隐式具有“any”类型。

我需要改变什么或者我的方法完全错误?
当接口是构造函数参数时,它也是在构造函数中设置默认属性的好解决方案。

编辑:
关于条目,我真的很喜欢它们,所以我使用以下代码:

//extensions.d.ts
interface Object
{
    entries<T>(o: any): [string, T][];
    entries(o: any): [string, any][];
}
//exntesion.js !!note js not ts
if (!Object.entries)
{
    Object.entries = function* entries(obj)
    {
        for (let key of Object.keys(obj))
        {
            yield [key, obj[key]];
        }
    };
}

编辑2:

其主要思想是解决重载构造函数的问题,在重载构造函数中只能设置所需的属性
如果其他人认为完整的代码可用,请参阅下面的代码。

interface IMy
{
    prop1?: boolean;
    prop2?: string;
    prop3?: string;
    prop4?: number;
}

class MyClass implements IMy
{
    prop1: boolean = false;
    prop2: string = "";
    prop3: string = "Something";
    prop4: number = 0;

    constructor(properties: IMy)
    {
        this.assing(properties);
    }

    assing(o: IMy): void
    {
        let that = (<any>this);
        for (let key in o)
        {
            if (o.hasOwnProperty(key))
            {
                let value = (<any>o)[key];
                if (typeof value !== "undefined" && typeof that[key] !== "undefined")
                    that[key] = value;
            }
        }
    }

}

let my1 = new MyClass({ prop1: true });
let my2 = new MyClass({ prop2: "SomeText", prop3: "Anything" });
//I set prop2 and prop3
let my3 = new MyClass({ prop4: 10 });    
//I set prop4 (fourth parameter)

console.log(my1, my2, my3);

共有2个答案

李兴庆
2023-03-14

在TypeScript 2.1中,更好的方法是使用keyof和映射类型。

function test()
{
    const my = new MyClass();
    my.assign({ prop1: 3});
}


type MyClassPartial = {
    [P in keyof MyClass]?: MyClass[P];
};

class MyClass
{
    prop1: number;
    prop2: string;
    assign(props: MyClassPartial)
    {
        for (const key of Object.keys(props))
        {
            this[key] = props[key];
        }
    }
}
谷涵容
2023-03-14

错误本身来自--noImplicitAny编译器选项。如果您删除它,错误就会消失。但我相信,拥有它并不是一件坏事。

您需要以某种方式向key添加类型注释,这在for... of循环中似乎没有问题。

我认为这种方法不错,但您需要以稍微不同的方式重写属性上的迭代。

另一方面,我假设您的目标也是ES6(为了让编译器不抱怨.entries(),它看起来像ES6的特性)。它看起来像是用于数组,而不是对象。

编辑:

受另一个SO答案的启发-为了消除错误,您可以向任何添加强制转换,如下所示:

(<any>this)[key] = value;

上面介绍了如何使用。条目()仍然适用。

 类似资料:
  • 我想给一个对象里所有值为null的属性赋其它值,比如: 有没有大佬知道 assignDefaults 这个函数如何实现?

  • 问题内容: 假设我创建了一个类的实例,并想为其公共属性分配一些值。通常,这将是这样完成的: 但是,如果编写一个将类作为参数的函数,而我想动态地为该类的公共属性分配一些值,那就是通过变量和循环(不知道有多少个或被称为什么)。 ) 显而易见的是: 但这是行不通的。 有任何想法吗? 问题答案:

  • 问题内容: 在这里,我使用例如动态生成html元素 我想为ng-model设置类型值。是否有可能或者我想像这样为ng-true-value设置类型值 问题答案: 由于ng-repeat为每种类型/项目/迭代创建子范围,因此我们需要将每种类型的ng-model与父范围而不是子范围相关联。一种方法是使用$ parent: 如果像在@Alex的答案中那样定义$ scope.types,则如果单击相应的复

  • 比方上面的类型,如果我想要 value 的类型在type为 'string' 时为 string ,在 type 为 'number' 的时候为 number。 要怎么定义这两个属性之间的类型约束?

  • 我希望data是否必传由A[T]是否有必传属性决定。如何做呢?

  • 问题内容: 我的问题很简单,我有一个以下JSON Typescript对象,并且我想迭代遍历JSON属性 使用的代码是以下有角TypeScript组件: 我真正需要的是遍历JSON的键值属性,并在我的HTML中显示它们。 非常感谢! 问题答案: 如果您使用的是Angular 6.1,请使用键值管道 对于Angular 5 示例:https://stackblitz.com/edit/keyvalu

  • 问题内容: 我有一个Python类,其属性名为:date1,date2,date3等。 在运行时,我有一个变量i,它是一个整数。 我想要做的是基于i的值在运行时访问适当的date属性。 例如, 如果i == 1,我想访问myobject.date1 如果i == 2,我想访问myobject.date2 我想为类而不是属性做类似的事情。 例如,我有一堆类:MyClass1,MyClass2,MyC

  • 为什么需要这样AddDataType<'AlarmTips'> 才能正确获取类型? 不是已经使用 <T>进行关联了吗?