David Thielen
David Thielen

Reputation: 33006

Can a typescript var in an interface be declared of type A or B

We are setting up our class constructors to take an interface of the class for the copy constructor. So basically:

interface IPoint {
    var x : number;
    var y : number;
}

class Point implements IPoint {
    var x : number;
    var y : number;

    constructor (src : IPoint) {
        this.x = src.x;
        this.y = src.y;
    }

    public getTotal() : number {
        return x + y;
    }
}

We do this because we get this objects as JSON from a REST server and also pass the objects to/from a web worker. In these cases the object we receive is the interface, we have the data, but not the methods. The copy constructor works great for both the case of creating one from a full object as well as just the JSON.

But we hit a problem for the following case:

interface IPoint {
    var coordinates : (List or number[])
}

class Point implements IPoint {
    var coordinates : List

    constructor (src : IPoint) {
        // do an isArray() to initialize
    }

    public getTotal() : number {
        return // sum of all coordinates in the list
    }
}

When we get the object from JSON, coordinates is an array. In the object it is a List (from collections.ts).

We're presently defining "coordinates : any" in the interface which does work. But it truly should always be one of two types. Is there any way to declare it that way? There's no difference at runtime doing this, but it does make for better type checking.

Upvotes: 0

Views: 254

Answers (3)

basarat
basarat

Reputation: 276255

But it truly should always be one of two types.

Union types https://github.com/Microsoft/TypeScript/issues/14 are still to be implemented in typescript.

You can use any as you already know or you can use two variables with different types and assign appropriately.

Upvotes: 0

Nikola Dimitroff
Nikola Dimitroff

Reputation: 6237

Well, assuming that List supports the [] operator, you can do this:

interface IIndexable<T> {
    [index: number]: T
}

interface IPoint {
    coordinates : IIndexable<number>
}

Upvotes: 1

wjohnsto
wjohnsto

Reputation: 4463

My suggestion would be to define a set type for coordinates (List or number[]), and make sure the constructor can take in either and then convert whatever the input is to the type you need.

Upvotes: 2

Related Questions