Не стоит ли использовать @Builder (toBuilder = true) вместо сеттеров? - PullRequest
1 голос
/ 04 апреля 2019

Я всегда стараюсь сделать свой код полностью неизменным и вообще не использовать сеттеры.

Когда мне нужно обновить объект, dto или сущность, я использую @Builder(toBuilder = true) вместо сеттеров.

public Car updateCar(final String id) {
    final Car existing = carRepository.getById(id);
    final Car.CarBuilder builder = existing.toBuilder().make("Mercedes-Benz");
    if (anyCondition) {
        builder.status("READY");
    }
    final Car updatedCar = builder.build();
    return carRepository.save(updatedCar);
}

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

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

Какой подход вы предпочитаете: сеттеры или toBuilder?

P.S .: приведенный выше фрагмент кода просто для лучшего понимания того, как я использую toBuilder

1 Ответ

2 голосов
/ 04 апреля 2019

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

Вы задаете нам и себе неправильный вопрос.
Вы не должны беспокоиться о производительности для таких простых классов с носителем данных.
Контрольный ориентир (см. JMH ) и см.

Но с чисто теоретической точки зрения единственными издержками являются создание другого объекта (размер которого в памяти зависит от расположения его членов), дополнительный шаг передачи примитивных значений / ссылок из экземпляр экземпляра для результирующего экземпляра (может быть, еще больше работы для GC? Я бы даже не учел это).
Таким образом, еще несколько циклов процессора.

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


Возьми этот класс

public class Car {
    private String maker;
    private int year;
    private int kms;

    // Getter - setters
}

Размер составляет примерно 16 + 4 + 4 + 4 = 28 байт.
Теперь, используя строитель, такой как

public class CarBuilder {
    private String maker;
    private int year;
    private int kms;

    public CarBuilder setMaker(final String maker) {
        this.maker = maker;
        return this;
    }

    public CarBuilder setYear(final int year) {
        this.year = year;
        return this;
    }

    public CarBuilder setKms(final int kms) {
        this.kms = kms;
        return this;
    }

    public Car createCar() {
        return new Car(maker, year, kms);
    }
}

Размер по-прежнему составляет примерно 16 + 4 + 4 + 4 = 28 байт.

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


После редактирования, возможно, вы пытаетесь сделать Объединение объектов ?
В этом случае рассмотрим Apache Commons Pool .

...