Не нарушает ли внедрение зависимостей умными указателями принцип единой ответственности?

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

Итак, нарушает ли это SRP - при условии, что класс уже несет некоторую ответственность.

Несколько простых примеров:

  class Calculator {
  public:
      Calculator(std::unique_ptr<Adder> adder) : adder(adder) {}
      void add();
  private:
      std::unique_ptr<Adder> adder;
  };

Когда дизайн изменится - поэтому у меня будет много разных калькуляторов - тогда мне нужно изменить unique_ptr в shared_ptr, Так что даже если Calculator Основная ответственность (для расчета) не изменилась - мне нужно сменить класс.

Не лучше ли использовать простые ссылки для внедренных объектов - и просто оставить ответственность за время жизни внедренных объектов за другими классами?

0 ответов

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

Чтобы проиллюстрировать это - вы можете инкапсулировать доступ к своим членам некоторым частным методом - это предотвращает изменения в реализации класса, когда вы переходите с unique_ptr к shared_ptr или наоборот.


private:
   Adder& add();
   Adder const& add();

Или вы можете пойти еще дальше и приложить сумматор к какому-то частному объекту, что полностью предотвратит случайный доступ к "прочитанной" переменной сумматора, например:

class Calculator 
{
   class AdderProxy
   {
   public:
       using Type = std::unique_ptr<>;
       AdderProxy(AdderType);
       void add(...);    
   };
public:
   Calculator(AdderProxy::Type);

private:
   AdderProxy adder;

Или вы можете просто иметь некоторую библиотеку DI, как этот один - и есть все виды инъекций скрытых от кода приложения.