Сеттерные методы или конструкторы

До сих пор я видел два подхода к установке значения переменной в Java. Иногда используется конструктор с аргументами, другие методы setter используются для установки значения каждой переменной.

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

Но когда мы используем конструкторы и когда мы используем сеттеры?

Ответ 1

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

Вы устанавливаете значение с помощью подхода setter, когда вы хотите изменить значение поля после создания объекта.

Например:

MyObject obj1 = new MyObject("setSomeStringInMyObject"); // Constructor approach
// Yippy, I can just use my obj1, as the values are already populated
// But even after this I can change the value
obj1.setSomeString("IWantANewValue"); // Value changed using setter, if required.
..
MyObject obj2 = new MyObject();
obj2.setSomeString("setSomeStringNow"); // Setter approach
// values weren't populated - I had to do that. Sad :(

И как отметил Аксель, если вы хотите создать неизменяемые объекты, вы не можете использовать метод setter-methods. Я не буду говорить, что все должно быть инициализировано в конструкторе, потому что существуют разные подходы, такие как ленивая оценка, которую можно использовать даже с неизменяемыми объектами.

Ответ 2

Если вы хотите, чтобы конструктор с неизменяемым классом использовал конструкторы, используйте seters.

Ответ 3

Скажем, у нас есть класс с именем Counter:

public class Counter{
    int count;
    //constructor
    public Counter(int c){
        count = c;
    }
    public void setCounter(int newCounter){
        count = newCounter;
    }
}

В вышеприведенном классе, когда вы хотите создать новый объект Counter, вы должны использовать конструктор и установить в нем переменную count. так:

Counter myCounter = new Counter(1);

Если вы хотите изменить переменную count во время выполнения, вы должны использовать метод setter:

myCounter.setCounter(2);

Ответ 4

Это зависит от области приложения и назначения класса в нем.

Java beans обычно имеет конструктор arg и getter/setters для соответствующих переменных-членов. Преимущество такого подхода заключается в том, что Java beans поддерживается из коробки во многих инфраструктурах, таких как Struts и Spring.

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

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

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

1 - Хотя, рекомендуется, чтобы дизайн класса не зависел от фреймворков. Хорошие структуры, такие как Spring, не обеспечивают соблюдение таких требований.

Ответ 5

В большинстве случаев я использую оба из них:) (так как вы 9/10 раза хотите вернуться и что-то изменить (и это не очень полезно для создания нового экземпляра)

Я обычно делаю что-то вроде tihs

public class User {

    private int id;
    private String initials;
    private String firstName;
    private String lastName;
    private String email;

    public User() {
        this(0, "", "", "");
    }

    public User(int id, String firstName, String lastName, String email) {
        this.id = id;
        this.firstName = firstName;
        this.lastName = lastName;
        this.email = email;
    }
   // Getters and setters should be here
}

И когда вы хотите что-то редактировать, вы можете просто использовать сеттеры (хорошо, если вы, например, сохраняете своих пользователей в ArrayList, тогда вы можете просто получить объект от arraylist и просто установить поле вы хотите отредактировать, вместо того, чтобы создать совершенно новый объект:)

Ответ 6

Вы можете объединить два аспекта. Внутри конструктора вы можете вызвать установщики переменных instace. Что-то вроде:

public class TestClass {
    private String someField;

    public TestClass(String someField) {
        setSomeField(someField);
    }

    public String getSomeField() {
        return someField;
    }

    public void setSomeField(String someField) {
        this.someField = someField;
    } 
}

Ответ 7

Мы используем этот подход в зависимости от сценария.

  • Если у нас есть набор значений при создании объекта класса, тогда мы будем использовать конструкторный подход.

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

Ответ 8

В случае конструкторов, когда вы обновляете поля, каждый раз вы создаете новый объект, используя новое ключевое слово.

Customer customer = new Customer("Tom", 23, 10000);

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

В случае методов setter вы можете установить отдельные поля только в исходном объекте.

Ответ 9

Я думаю, вы задали хороший вопрос: - Но когда мы используем конструкторы и когда мы используем сеттеры?

Сначала начнем с некоторых понятий, я надеюсь, что это объяснение поможет всем, кто хочет знать, когда использовать конструкторы или методы seters() и getters() (Accessors and Mutators). Конструкторы похожи на Методы, однако в конструкторе конструктор и существует несколько различий:

1) Конструктор используется для инициализации состояния объекта. Метод используется для отображения поведения объекта.

2) Конструктор не должен иметь тип возврата. Метод должен иметь тип возврата.

3) Конструктор вызывается неявно. Метод вызывается явно.

4) Getters() или аксессоры - это методы, обеспечивающие доступ к переменным экземпляра объекта. Setters() или мутаторы - это методы, которые предоставляют вызывающему абоненту возможность обновлять значение конкретной переменной экземпляра.

Учитывая это, подумайте о терминах объектно-ориентированного программирования (ООП), чтобы удовлетворить требования директоров ООП (Ориентированное на объекты программирование (ООП) построено по четырем основным принципам: Инкапсуляция, Абстракция данных, Полиморфизм и Наследование.), методы Getter() и Setter() - это ключ к достижению этого.

Вот формула, которая покажет вам, что я имею в виду:

Частные поля + Публичные accessors == Инкапсуляция;

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

Здесь я собираюсь предоставить вам два класса, я добавил комментарий к нему, чтобы попытаться объяснить сам код. Возьмите эти классы как лабораторию по методам с Customer и TestCustomer [тем, у кого есть метод main()], вы можете скопировать код и запустить его самостоятельно. Примечание. Я использовал два конструктора, чтобы объяснить класс, имеющий несколько конструкторов, и методы public setters() и getters() для доступа к частным переменным экземпляра:

package com.exercise.lecture2;

/**
 * 1) Create a Customer class that has the following attributes:
 * name, SSN.
 * 2) This class shoud have two methods: getName() and getSSN().
 * 3) If the class is instantiated with only a SSN, then give the default name of "John Doe". (HINT: Use two constructors)
 * 4) Also, add a method toString(), that returns a string representation of the customer object (name and SSN concatenated).
 *      Make sure to set this method public.
 * 5) Create a class to test your program (e.g. a class that include the main() method). In your test program, instantiate
 *      three customers and print out the value using toString() method.
 * 
 * @author Samuel M.
 *
 */

//this class is complemented with class  TestLabCustomer.java
public class LabCustomer {
    private String name;
    private int socialSecurityNum;

    // constructors
    public LabCustomer(String name, int socialSecurityNum) {
        this.name = name;
        this.socialSecurityNum = socialSecurityNum;
    }

    /** The keyword 'this' can be used to call a constructor from a constructor,
     * when writing several constructor for a class, there are times when
     * you'd like to call one constructor from another to avoid duplicate code.
     */
    // Account with This() on a second constructor
    public LabCustomer(int socialSecurityNum) {
        this("John Doe", socialSecurityNum); // default name is printed if only the SSN is provided
    }

    // getters and setters
    String getName() {
        return name;
    }

    void setName(String name) {
        this.name = name;
    }

    int getSSN() {
        return socialSecurityNum;
    }

    void setSSN(int socialSecurityNum) {
        this.socialSecurityNum = socialSecurityNum;
    }


    // instance method
    public String toString() { //overriding the toString() method 
        return ("Customer name: " + getName() + ", SSN#: " + getSSN() ); // concatenating the name and SSN

    }
}

Вот тестовый класс, который имеет метод main() и вызывает метод экземпляра после создания экземпляра класса предпросмотра:

package com.exercise.lecture2;

//this class is complemented with class  LabCustomer.java
public class TestLabCustomer {

    public static void main(String[] args) {
        // Instantiating an object of class LabCustomer and creating three customers objects
        LabCustomer cust1 = new LabCustomer("Juan Melendez", 123457789);
        LabCustomer cust2 = new LabCustomer("Mary Lee", 125997536);
        LabCustomer cust3 = new LabCustomer(124963574); // when instantiating with no "name", the default (John Doe) is printed 

        /**
         * Once you've instantiated an object and have an object variable,
         * you can use object variable to call an instance method. 
         *  e.g.:
         *  object variables: cust1, cust2, cust3
         *  call the method toString() using the object variable and dot [.] in order to perform the method call.
         */
        // calling method toString() in class LabCustomer to print customer values
        System.out.println(cust1.toString());
        System.out.println(cust2.toString());
        System.out.println(cust3.toString());

    }

}

результат:

Имя клиента: Хуан Мелендес, SSN №: 123457789

Имя клиента: Mary Lee, SSN #: 125997536

Имя клиента: John Doe, SSN #: 124963574