如何在TypeScript中正确更改变量的类型?

vptzau2j  于 2023-05-01  发布在  TypeScript
关注(0)|答案(5)|浏览(183)

感谢您的耐心,我刚刚开始使用TypeScript。
我正在开发一个angular 2应用程序,它需要接受文本输入,然后进行一系列计算。我(不正确地?)假设我需要首先将输入绑定到我的数据模型中的“任何”类型变量,然后将这些变量转换为数字以便处理数字。我已经找遍了所有的地方,找不到如何以这样一种方式做到这一点,它不会抛出这个TS编译器错误:

`src/calculator_service.ts(40,5): error TS2322: Type 'number' is not assignable to type 'string'.`

在我的CalculatorService中,我有这个函数:

/*
 * Convert the object of strings recieved from the form into a clean object of integers
 */
n(model:ModelFields) {
    // Clone it
    this.numericModel = Object.assign({}, this.model);

    for (var prop in this.numericModel) {
        if (this.numericModel.hasOwnProperty(prop)) {

            // strip off all non-numeric charactersklj
            this.numericModel[prop] = this.numericModel[prop].replace(/\D/g,'');

            // convert to Any typescript type
            // this breaks the application, and still throws a compiler error. nope.
            // this.numericModel[prop] = this.numericModel[prop]:Any;

            // convert to Number type
            // this gives a typescript console error, but seems to still compile... 
            // ignoring this for now in order to meet deadline
            this.numericModel[prop] = +this.numericModel[prop];

        }
    }

    return this.numericModel;
}

和ModelFields定义(感谢tarh!)

export class ModelFields { 
    constructor( 
        public fieldName: any, 
        public anotherField: any 
    ) 
    {} 
}

有什么想法吗?谢谢大家!

syqv5f0l

syqv5f0l1#

你不能在TypeScript中更改变量的类型,这与TS的目的正好相反。相反,您可以将变量声明为“any”,这相当于JS中的经典“var”变量,无类型。
一旦声明了变量,就不能重新键入它。但是,您可以做的是声明“any”,然后在需要使用它时对其进行强制转换,以便将其用作所需的类型。
例如,这不会抛出任何错误:

let a: any;

a = 1234;
(a as number).toExponential();

a = "abcd"; 
(a as string).substr(1, 4);

对于你的类,这也是正确的,没有类型错误:

class ModelFields { 
    constructor( 
        public fieldName: any, 
        public anotherField: any 
    ) 

    //...
}

let model: ModelFields = new ModelFields(1, 2);

console.log(model.fieldName + model.anotherField);    // --> 3

model.fieldName = "a";
model.anotherField = "b";

console.log(model.fieldName + model.anotherField);    // --> ab
uxhixvfz

uxhixvfz2#

你的例子不够清楚,但我猜你的问题是因为Typescript inference

var x = 3; // x is a number
x = "45";  // compiler error

但是,如果您这样做:

var x : any = 3; // x can be anything
x = "45";

或者:

var x; // x is any forever
x = '45';  // x is still any

你可以在这些精彩的幻灯片和文档中找到更多的细节
希望这能帮上一点忙。..

hlswsv35

hlswsv353#

您可以通过省略旧类型中的属性,然后将其添加回来来创建新类型。
这将**不工作。

interface DbItem {
 _id: Buffer
 date: number
}

interface JsItem extends DbItem {
 _id: string
}

但是,您可以使用实用程序类型Omit来省略要更改的类型,然后再将它们添加回去。

interface DbItem {
 _id: Buffer
 date: number
}

interface JsItem extends Omit<DbItem, '_id'> {
 _id: string
}
wlsrxk51

wlsrxk514#

面对类似的问题,为我工作。

我的案例:

article Id来自路由参数的字符串格式,从API中我获得数字格式的数据。
如果我检查!=,ES lint抛出错误。所以我使用Number()方法在vanilla javascript中将字符串转换为数字。

const articleId = Number(this.route.snapshot.params['articleId']);

data.forEach((element, index) => {

    // console.log(typeof(element['id']), element['id']); 
    // 4, number
    // console.log(typeof(this.route.snapshot.params['articleId']), this.route.snapshot.params['articleId']);
    // 4, string (converted to number)

    if (element['id'] !== articleId) {
        //my implementation
     }
}

参考链接:

  1. https://gomakethings.com/converting-strings-to-numbers-with-vanilla-javascript/
ulydmbyx

ulydmbyx5#

重新声明变量:

// Re-declare the variable

let value: any = Date.now() % 2 === 0 ? "string" : 124875;
if (typeof value === 'string') {
  let str: string = value as string;
} else {
  let num: number = value as number;
}

或Map到另一个类示例:

export class ModelField {
  constructor(public fieldName: any) {}
}

export class StringField { 
    public x: string; 
    constructor(model: ModelField) {
      this.x = model.fieldName as string;
    } 
}

let value: any = Date.now() % 2 === 0 ? "string" : 124875;
let model: ModelField = new ModelField(value);
if (typeof model.fieldName === 'string') {
  let strField: StringField = new StringField(model);
} else {
  let numField: NumberField = new NumberField(model);
}

相关问题