Так, є і недоліки
Код, який легко читати, є хорошим, але також остерігайтеся того, що код також повідомляє . Коли методи об'єкта завжди повертають об'єкт, він передає пару речей:
- Мені потрібна розширена конфігурація, яка не обов'язково очевидна, в якому порядку слід встановлювати або налаштовувати речі
- Кожен наступний виклик методу будується на останньому
Дійсний випадок використання: Спеціальні запити до бази даних
Бібліотеки класів існують майже всіма мовами, що дозволяє запитувати базу даних, не вдаючись до жорстко кодованого SQL. Візьмемо приклад Entity Framework для .NET:
DBContext db = new DBContext();
List<Post> posts = db.Posts
.Where(post => post.Title.Contains("Test"))
.OrderBy(post => post.DateCreated)
.ToList();
Це вільний інтерфейс, де кожен наступний виклик методу будується на попередньому. Читання цих дзвінків логічно має сенс у контексті запитів до бази даних.
Недійсний випадок використання: синтаксичний цукор для налаштування властивостей
Тепер давайте скористаємось тим же шаблоном, що і для Post
класу:
public class Post
{
public string Title { get; set; }
public DateTime DateCreated { get; set; }
public string Body { get; set; }
public Post SetTitle(string title)
{
Title = title;
return this;
}
public Post SetDateCreated(DateTime created)
{
DateCreated = created;
return this;
}
public Post SetBody(string body)
{
Body = body;
return this;
}
}
Тепер давайте розглянемо, як би ви використовували цей клас:
Post post = new Post()
.SetTitle("Test")
.SetDateCreated(DateTime.Now)
.SetBody("Just a test");
Коли я бачу цей код, я одразу задаю це запитання: "Після дзвінка SetBody
чи запитує базу даних? Чи потрібно мені викликати інший метод, щоб сказати:" Я закінчую? "
Що ланцюжкові дзвінки методу повідомляють коду за допомогою Post
класу?
- У мене складна установка
- Кожен виклик методу будується на попередньому
Це насправді правда? Ні. Post
Клас не має складних налаштувань. Визначаючи назву, створену дату та тіло, не будуйте один одного на більш складній кінцевій цілі. Ви розім'яли квадратний кілочок в круглий отвір.
Недоліком ланцюга самореференціальних методів є те, що ви повідомляєте, що для того, щоб щось зробити, потрібні кілька викликів методів, і що кожен виклик формується останнім. Якщо це не відповідає дійсності, тоді ланцюжок методів може бути неправильним повідомленням інших програмістів.
Коли ваші колеги сказали:
Вільні інтерфейси повинні бути реалізовані не для зручності, а для семантики
Вони були абсолютно правильні. Вільний інтерфейс або ланцюжок методів передає щось саме по собі, що може бути неправдою.