Подтвердить что ты не робот

Конструктор со всеми свойствами класса или конструктором по умолчанию с сеттерами?

Ниже приведены два подхода:

  • конструктор со всеми свойствами класса

Плюсы: я должен указать точное количество типов параметров, поэтому, если я сделаю ошибку, компилятор предупреждает меня (кстати, есть ли способ предотвратить проблему ошибочного переключения двух целых чисел в список параметров? )

Минусы: если у меня много свойств, строка создания может стать очень длинной и может охватывать две или более строки

  • seters и пустой конструктор по умолчанию

Плюсы: я могу ясно видеть, что я устанавливаю, поэтому, если я что-то делаю неправильно, я могу определить его, как только я его набираю (я не могу сделать ошибку previuos при переключении двух переменных тот же тип)

Минусы: создание объекта с большим количеством свойств может занять несколько строк (не знаю, действительно ли это конфликт), и если я забыл установить свойство, компилятор ничего не говорит.

Что вы будете делать и почему? Вы знаете какой-либо световой шаблон (считайте, что он должен использоваться каждый раз, когда создается объект wth 7+)? Я спрашиваю об этом, потому что я склонен не любить большие конструкторы, где я не могу быстро найти, где находится переменная, которую я ищу, с другой стороны, я обнаружил, что "все свойства" уязвимы для отсутствия некоторых свойств.

Не стесняйтесь аргументировать свои предположения в плюсах и минусах, поскольку они - только мои мысли:)

Обновление - вопрос, который я нашел, связанный с этим: Создание больших, неизменяемых объектов без использования конструкторов с длинными списками параметров

4b9b3361

Ответ 1

Вы можете посмотреть шаблон Builder, предложенный Джошуа Блох, и описанный в Эффективной Java. Там презентация с основными моментами на http://developers.sun.com/learning/javaoneonline/2007/pdf/TS-2689.pdf; без сомнения, вы могли бы найти лучшую ссылку.

В принципе, у вас есть другой класс, возможно, внутренний класс, который предоставляет методы, названные в честь установленных свойств, и которые возвращают исходный строитель, чтобы вы могли связывать вызовы. Это делает довольно читаемый фрагмент кода.

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

Message message = new Message.Builder()
    .sender( new User( ... ) )
    .recipient( new User( ... ) )
    .subject( "Hello, world!" )
    .text( messageText )
    .build();

Фрагмент Message.Builder может выглядеть примерно так:

public class Builder {

    private User sender = null;
    // Other properties

    public Builder sender( User sender ) {
        this.sender = sender;
        return this;
    }
    // Methods for other properties

    public Message build() {
        Message message = new Message();
        message.setSender( sender );
        // Set the other properties
        return message;
    }

}

Ответ 2

Вы пропустили самый большой pro из конструктора с множеством параметров: он позволяет создавать неизменные типы.

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

Ответ 3

Недавние академические исследования (CMU и Microsoft) по удобству использования API говорят о том, что конструкторы по умолчанию с сеттерами будут способом использования в плане удобства использования. Это от "Юзабилити-последствий требуемых параметров в конструкторах объектов" Джефф Стилос и Стивена Кларка и был представлен на Международной конференции по разработке программного обеспечения:

Аннотация: Удобство использования API-интерфейсов становится все более важным для производительности программистов. Основываясь на опыте изучения юзабилити конкретных API, были изучены методы изучения удобства использования дизайна, характерного для многих API. Было проведено сравнительное исследование для оценки того, как профессиональные программисты используют API-интерфейсы с требуемыми параметрами в конструкторах объектов, а не без параметров "конструкторы по умолчанию". Было выдвинуто предположение, что требуемые параметры создадут более удобные и самодокументирующие API, направляя программистов на правильное использование объектов и предотвращая ошибки. Однако в исследовании было установлено, что, вопреки ожиданиям, программисты настоятельно предпочитают и более эффективны с API, которые не требуют параметров конструктора. Поведение участников анализировалось с использованием рамки когнитивных измерений и показало, что требуемые параметры конструктора мешают общим стратегиям обучения, что вызывает нежелательные преждевременные обязательства.

Ответ 4

Вы упомянули об этом в своем сообщении, но я думаю, что это важный момент, заслуживающий большего внимания: если каждый входной параметр не является другим типом, большая проблема с огромными конструкторами заключается в том, что очень легко транспонировать пару переменных. Компилятор является ненадежной защитной сетью - он поймает некоторые ошибки, но те, которые проскальзывают, будут намного сложнее идентифицировать и отлаживать. Тем более, что список ввода для огромного конструктора довольно непрозрачен, если вы не открыли API в другом окне.

Getters и seters намного легче отлаживать, особенно если вы устанавливаете гарантии, которые генерируют исключение во время выполнения, если объект неправильно заполнен. И я большой поклонник "легко отлаживать".

До этого потока я никогда не слышал о шаблоне Builder, о котором говорит Роб. Никогда не использовал его сам (очевидно), но он проклят интригующим.

Ответ 5

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

Например, если у вас есть что-то вроде этого:

class Contact
{
    public Contact(string firstName, string lastName, string phoneNumber,
        string street, string city, string state, int zipCode) { ... }
}

Я бы реорганизовал его:

class Contact
{
    public Contact(Person person, PhoneNumber number, Address address) { ... }
}

class Person
{
    public Person(string firstName, string lastName) { ... }
}

class PhoneNumber
{
    public PhoneNumber(string digits) { ... }
}

class Address
{
    public Address(string street, string city, string state, int zipCode) { ... }
}

Слишком большие классы - это действительно общая проблема проектирования в кодовых базах ООП.

Ответ 6

Есть и другие аспекты. Если вы хотите иметь возможность выполнять определенные действия с вашим классом во время разработки, а не только во время выполнения, например, добавляя свой класс в качестве объекта в палитре объектов (это Java с использованием Netbeans), вам необходимо предоставить конструктор без аргументов в чтобы иметь возможность сделать это.

Ответ 7

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

Ответ 8

и пустой конструктор по умолчанию

JRL косвенно коснулся его, но одной из причин рассмотрения использования сеттеров является соответствие объекта Спецификация JavaBean. Это позволяет экземплярам поддаваться редактированию с помощью средств интроспекции и настойчивости с помощью сериализации методы.

Ответ 9

Кто говорит, что вы не можете сделать то и другое? Я бы сказал, что обязательные свойства входят в конструктор, а дополнительные - обработчиками. BTW, который говорит, что вам всегда нужен один сеттер на собственность? Если два свойства принадлежат вместе концептуально, почему бы не установить их вместе?

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