На мой взгляд, то же самое относится и к TypeScript. Не полагайтесь на то, что IDE даст вам подсказки о том, что делает код. Лучше всего, чтобы код говорил вам, что он делает.
Чем больше у вас аргументов, тем менее читаемым становится ваш код
Возьмите следующий код:
sendMsg("Poem", "I sing of brooks, of blossoms, birds and bowers.", new Date(2015, 9, 20));
Мы могли бы сказать, что первый аргумент — это заголовок, а второй аргумент — это тело, но что делает третий аргумент? Что означает здесь дата?
Мы должны посмотреть на сигнатуру функции, чтобы увидеть:
function sendMsg(title: string, body: string, dateToSend = new Date())
Итак, теперь мы знаем, что такое третий параметр, но даже несмотря на то, что мы используем TypeScript, нам все равно пришлось провести некоторое исследование и посмотреть на сигнатуру функции. В качестве альтернативы мы могли бы навести указатель мыши на вызов функции для нашей среды разработки, чтобы сообщить нам, но это все еще не идеально.
Слишком много аргументов затрудняет внесение изменений и увеличивает вероятность ошибки
Теперь предположим, что мы хотели добавить новый обязательный параметр даты с именем dateToSendAgain
. Сигнатура нашей функции меняется на это:
function sendMsg(title: string, body: string, dateToSendAgain: Date, dateToSend = new Date())
Проблема в том, что наш первоначальный вызов функции не вызывает ошибку компиляции, и смысл изменился:
// now creates a message with dateToSendAgain = new Date(2015, 9, 20)
// and dateToSend = new Date()
sendMsg("Poem", "I sing of brooks, of blossoms, birds and bowers.", new Date(2015, 9, 20));
Несмотря на то, что изначально мы планировали, что dateToSend
будет new Date(2015, 9, 20)
, теперь это new Date()
, и, возможно, мы не хотели, чтобы dateToSend
было new Date(2015, 9, 20)
.
Вместо этого используйте объект со свойствами
Мы могли бы решить все это, если бы наша исходная сигнатура функции использовала объект со свойствами (обратите внимание, что интерфейс не требуется):
function sendMsg(options: { title: string; body: string; dateToSend?: Date; dateToSendAgain: Date; }) {
// we now have to define our default values here though...
// if we use destructuring it's not too bad:
const {title, dateToSend = new Date()} = options;
// ...rest of function body omitted...
}
Таким образом, наш исходный код выглядел бы так:
sendMsg({
title: "Poem",
body: "I sing of brooks, of blossoms, birds and bowers.",
dateToSend: new Date(2015, 9, 20)
});
... что очень легко быстро понять, что происходит.
Кроме того, когда мы добавим dateToSendAgain
, это будет очень просто, и мы получим ошибку компиляции, информирующую нас о необходимости обновить все наши вызовы функций новым обязательным свойством:
sendMsg({
title: "Poem",
body: "I sing of brooks, of blossoms, birds and bowers.",
dateToSend: new Date(2015, 9, 20),
dateToSendAgain: new Date(2015, 10, 20)
});
Предложение
Мое предложение было бы:
- Используйте несколько параметров, когда их не слишком много, и вы можете понять значение каждого аргумента, взглянув на имя функции.
- В противном случае используйте объект со свойствами.
- Смешивание этих двух вместе нормально, если это читабельно.
Документация по свойствам объекта
TypeScript использует JSDoc для завершения кода, поэтому вы можете использовать этот синтаксис для документирования свойств объекта. Прочитайте здесь, как это задокументировать.
К сожалению, это не дает мне описания свойств объекта при завершении кода в Visual Studio 2013 с TS 1.6.
Однако использование интерфейса, похоже, работает:
/**
* The options for sendMsg
*/
interface SendMsgOptions {
/**
* The title of the message
*/
title: string;
// etc...
}
Изменение заголовка функции:
function sendMsg(options: SendMsgOptions)
Затем при его использовании вы можете увидеть комментарий в завершении кода:
![Завершение кода параметров сообщения](https://i.stack.imgur.com/BYgXK.png)
person
David Sherret
schedule
05.10.2015