2015-12-30 2 views
0

Я пытаюсь создать метод, который можно использовать в качестве общего решения для создания экземпляров разных классов с различными параметрами конструктора.Создание классов по ссылке на конструкторы с различным количеством параметров

Вот пример этого «мыслимых» метод, вроде мои мысли о том, как это должно выглядеть:

module flashist 
{ 
    export interface ISimpleClass<ObjectType> 
    { 
     new(): ObjectType; 
    } 

    export class Instantiator 
    { 
     public createInstance(Class: ISimpleClass<ClassType>, ...args): ClassType 
     { 
      // I understand, that this annotation is not possible 
      var result: any = new Class.apply(args); 
      return (result as ClassType); 
     } 
    } 
} 

Проблема происходит с линией:

var result: any = new Class.apply(args); 

Где я хочу, чтобы пройти неизвестные параметры конструктору. Я понимаю, что этот синтаксис невозможен, я просто хотел показать что-то похожее на то, чего хочу достичь.

Итак, мой вопрос: есть ли у нас какое-либо решение этой проблемы в TypeScript и/или JS?

ответ

0

Я Gound способ осуществить то, что мне нужно было с помощью функции Eval:

var evalString: string = "new Class("; 
args.forEach(
    (value: any, index: number, array: any[]): void => 
    { 
     if (index > 0) 
     { 
      evalString += ","; 
     } 
     evalString += "args[" + index + "]"; 
    } 
); 
evalString += ");"; 

var result: any = eval(evalString); 

я не уверен, если это нормальная практика для использования функции Eval (может быть, это некоторые неизвестные мне недостатки), но он работает для меня на нынешнем этапе.

1

Я не уверен, чего вы пытаетесь достичь, но я думаю, что есть два неоптимальных решения, которые могут удовлетворить ваш прецедент.

  1. Жесткий код параметров.

    public createInstance(Class: ISimpleClass<ClassType>, ...args): ClassType 
    { 
        var result:ClassType; 
        if (args.length == 0) 
         result = new ClassToCreate(); 
        if (args.length == 1) 
         result = new ClassToCreate(args[0]); 
        // ... 
        if (args.length == 8) 
         result = new ClassToCreate(args[0],args[1],args[2],args[3],args[4],args[5],args[6],args[7]); 
        // ... 
    
        return result; 
    } 
    

    Я знаю, выглядит уродливым.

  2. Object.create.

    public createInstance(Class: ISimpleClass<ClassType>, ...args): ClassType 
    { 
        var result:any = Object.create(ClassToCreate.prototype); // create an object 
        ClassToCreate.apply(result, args); // call the constructor 
    
        return result; 
    } 
    

Как я уже говорил, ни один из них не является оптимальным, но может помочь, пока вы не можете найти лучшее решение вашей проблемы. Может быть, передать только один словарь data в каждый конструктор?