| 
	| 
	
	| 
		
	| 
			
			 
			
				02.08.2017, 19:23
			
			
			
		 |  
	| 
		
			
			| Профессор       |  | 
					Регистрация: 04.10.2010 
						Сообщений: 571
					 
		
 |  |  
	| 
				ES6: Как сделать фабрику методов для класса?
			 Вопрос на самом деле по TypeScript, но он в этом плане полностью копирует ES6. 
Есть какой-то класс:
 
class Dog {
  bulk() {
    ...
  }
}
Нужно определять его методы не вручную, а динамически, примерно так:
 
function CreateMethod(params) {
  return function() {
     ...
  }
}
class Dog {
  bulk: CreateMethod({name: 'bulk', volume: 90}) //не работает
}
Как это сделать без декораторов методов?			 Последний раз редактировалось Shitbox2, 02.08.2017 в 19:29.
 |  |  
	| 
		
	| 
			
			 
			
				02.08.2017, 20:53
			
			
			
		 |  
	| 
		
			|  | Профессор       |  | 
					Регистрация: 25.10.2016 
						Сообщений: 1,013
					 
		
 |  |  
	| 
Dog.prototype.bulk = CreateMethod({name: 'bulk', volume: 90});
поскольку TypeScript заявлен как "надмножество", а class - как "сахар", то старый добрый способ должен работать, наверно. 
и да - понятно, что ссылки на super в методе bulk не будет.			 Последний раз редактировалось Alexandroppolus, 02.08.2017 в 21:01.
 |  |  
	| 
		
	| 
			
			 
			
				03.08.2017, 03:25
			
			
			
		 |  
	| 
		
			
			| Профессор       |  | 
					Регистрация: 04.10.2010 
						Сообщений: 571
					 
		
 |  |  
	| Так можно, но нужно именно в стиле ES6 
class Dog {
  bulk: CreateMethod({name: 'bulk', volume: 90})
}
Например, здесь  это делается с помощью интерфейса. Хотелось бы фабрику использовать |  |  
	| 
		
	| 
			
			 
			
				03.08.2017, 15:38
			
			
			
		 |  
	| 
		
			
			| Профессор       |  | 
					Регистрация: 04.10.2010 
						Сообщений: 571
					 
		
 |  |  
	| Rise,ну, это слишком жестко. Без eval'а нельзя разве?
 |  |  
	| 
		
	| 
			
			 
			
				03.08.2017, 17:51
			
			
			
		 |  
	| 
		
			
			| Профессор       |  | 
					Регистрация: 04.10.2010 
						Сообщений: 571
					 
		
 |  |  
	| Всё какие-то запрещённые методы у вас) Это всё равно, что глубокое сравнение объектов делать, сравнивая их json-строки |  |  
	| 
		
	| 
			
			 
			
				03.08.2017, 20:20
			
			
			
		 |  
	| 
		
			
			| Профессор       |  | 
					Регистрация: 04.10.2010 
						Сообщений: 571
					 
		
 |  |  
	| В TS можно так сделать. Будет работать. Правда, когда применяю к классу декоратор, все такие методы пропадают, но это я как-то декоратор неправильно пишу 
function CreateMethod(params) {
  return function() {
     console.log(params)
  }
}
class Dog {
  bulk = CreateMethod({name: 'bulk', volume: 90})
}
 |  |  
	| 
		
	| 
			
			 
			
				03.08.2017, 20:51
			
			
			
		 |  
	| 
		
			|  | Профессор       |  | 
					Регистрация: 25.10.2016 
						Сообщений: 1,013
					 
		
 |  |  
	| 
	
 
	| Сообщение от Shitbox2 |  
	| Правда, когда применяю к классу декоратор, все такие методы пропадают |  
	
 куда пропадают? |  |  
	| 
		
	| 
			
			 
			
				03.08.2017, 23:48
			
			
			
		 |  
	| 
		
			
			| Профессор       |  | 
					Регистрация: 04.02.2011 
						Сообщений: 1,815
					 
		
 |  |  
	| 
	
 
	| Цитата: |  
	| Правда, когда применяю к классу декоратор, все такие методы пропадают |  
	
 вероятно от того что все эти свойства в конструкторе создаются
				__________________Лучше калымить в гандурасе чем гандурасить на колыме
 			 Последний раз редактировалось DjDiablo, 03.08.2017 в 23:50.
 |  |  
	| 
		
	| 
			
			 
			
				04.08.2017, 12:27
			
			
			
		 |  
	| 
		
			
			| Профессор       |  | 
					Регистрация: 04.10.2010 
						Сообщений: 571
					 
		
 |  |  
	| Никуда не пропадают, это я неправильную реализацию написал. Если делать так, то всё работает: 
function logClass(target: any) {
  // сохраняем ссылку на исходный конструктор
  var original = target;
  // вспомогательная функция для генерации экземпляров класса
  function construct(constructor, args) {
    var c : any = function () {
      return constructor.apply(this, args);
    }
    c.prototype = constructor.prototype;
    return new c();
  }
  // новое поведение конструктора
  var f : any = function (...args) {
    console.log("New: " + original.name); 
    return construct(original, args);
  }
  // копируем прототип, чтобы работал оператор instanceof
  f.prototype = original.prototype;
  // возвращаем новый конструктор (он переопределит исходный)
  return f;
}
 |  |  
	| 
		
	| 
			
			 
			
				04.08.2017, 16:48
			
			
			
		 |  
	| 
		
			
			| Профессор       |  | 
					Регистрация: 04.10.2010 
						Сообщений: 571
					 
		
 |  |  
	| Пример декоратора, который я привел, не относится к задаче (т.е. он не участвует в определении методов). Просто я тестировал своё решение в т.ч. со сторонними декораторами, чтобы убедиться, что всё работает как надо.
 К сожалению, мой способ не работает в ES6 и это привязывает меня к TS
 |  |  |  |