The primary benefit of Typescript is to provide types for Javascript. And since [Typescript provides Generics](https://www.typescriptlang.org/docs/handbook/generics.html) - I don't think your implementation of a Dictionary provides any benefit over a plain javascript object.

In fact, as you noted in the comments, JS Objects (ie TS object) _are_ dictionaries. You just need to provide types around them for your dictionary. (btw - I also come from a C# background, but I've also come to love the underlying functional nature of JS that TS lets us type).

Here's a code sample of the direction I would expect a `Dictionary.ts` class to have in a code base I work in. Now that we have [Mapped Types](https://github.com/Microsoft/TypeScript/pull/12114), we can [generalize dictionaries better](http://www.rickcarlino.com/2017/02/27/Real-World-Use-Case-For-Typescript-Record-Types/).

    export interface Dictionary<K, V> {
      getKeys(): K[];
      getValues(): V[];
      get(key: K): V;
      put(key: K, val: V): void; // or boolean?
    }
    
    
    export class JSDictionary<K extends string, V> implements Dictionary<K, V> {
    
      private internalDict: Partial<Record<K, V>>;
    
      constructor() {
        this.internalDict = {};
      }
    
      public getKeys(): K[] {
        let keys: K[] = [];
        for(let key in this.internalDict) {
          keys.push(key);
        }
    
        return keys;
      }
    
      public getValues(): V[] {
        let vals: V[] = [];
    
        for(let key in this.internalDict) {
          vals.push(this.internalDict[key]);
        }
    
        return vals;
      }
    
      public get(key: K): V {
        return this.internalDict[key];
      }
    
      public put(key: K, val: V): void {
        this.internalDict[key] = val;
      }
    
    }


Example Usage

    type myKeys = 'FOX' | 'CAT' | 'DOG';
    
    interface Animal {
      species: string;
      name: string;
      weight: number;
    }
    
    // A dictionary that hols one fox/cat/dog.
    let myAnimalPen = new JSDictionary<myKeys, Animal>();
    
    myAnimalPen.put('FOX', { name: 'Foxworth', species: 'Fox', weight: 40 });
    
    // a dictionary that takes any string and maps it to a number
    let idDict = new JSDictionary<string, number>();
    idDict.put('somehas', 1204);
    idDict.put('yeahaasd', 3306);
    
    let yeaID = idDict.get('yeahaasd'); // yeaID is a number type
    let myFox = myAnimalPen.get('FOX'); // myFox is an Animal type


Major points:

- Code to an interface as much as you can in typescript. Affords you flexibility
- *Generic types*
- Transparent use of Plain JS object as the underlying dictionary (JS Engines optimize this very use case!)
- I removed overloaded constructors, but you could add that back in with the proper types and it will work as expected
- Left out clone - pretty easy to implement though
- No exception handling when get returns null, like your 'try*' functions. I actually like try functions like you have, so you could mostly copy/paste, although with the stricter typings sometimes that will be taken care of by the compiler for you.