Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Can you write a generic copy object function in typescript?

So far I've tried:

function copyObject<K, V> (object: { [k: K]: V; }) {
    var objectCopy = {};

    for (var key in object)
    {
        if (object.hasOwnProperty(key))
        {
            objectCopy[key] = object[key];
        }
    }

    return objectCopy;
}

But this gives a compiler warning: "Index signature parameter type must be 'string' or 'number'".

Maybe it's possible to constrain the key type to number or string? Or just overload it with both types as keys?

like image 399
AGD Avatar asked Mar 07 '14 10:03

AGD


2 Answers

You can simply do the following :

function copyObject<T> (object:T): T {
    var objectCopy = <T>{};

    for (var key in object)
    {
        if (object.hasOwnProperty(key))
        {
            objectCopy[key] = object[key];
        }
    }

    return objectCopy;
}

And usage:

// usage: 
var foo = {
    bar: 123
};

var baz = copyObject(foo);
baz.bar = 456;
like image 136
basarat Avatar answered Oct 06 '22 20:10

basarat


Typescript doesn't have typeclasses and I'm not aware of any interface that only string and number types satisfy so overloading seems to be the only option:

export function copyObject<V> (object: { [s: string]: V; }) : { [s: string]: V; }
export function copyObject<V> (object: { [n: number]: V; }): { [n: number]: V; }
export function copyObject (object: {}): {}
export function copyObject (object: {}) {
    var objectCopy = <any>{};

    for (var key in object)
    {
        if (object.hasOwnProperty(key))
        {
            objectCopy[key] = (<any>object)[key];
        }
    }

    return objectCopy;
}

(The string and number overloads allow you to copy objects with homogeneous types)

like image 45
AGD Avatar answered Oct 06 '22 21:10

AGD