2016-09-21 2 views
0

Я читал о шаблонах дизайна, и я заметил, что термин «непрозрачные зависимости» был весьма популярен. Некоторые источники утверждают, что:Что такое непрозрачные зависимости?

Непрозрачные зависимостей плохой вид зависимостей

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

Но я не очень хорошо понял.

Может ли кто-нибудь дать мне несколько примеров использования этих зависимостей и почему я должен их избегать?

+0

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

ответ

2

Например:

public class MyService 
{ 
    private IRepository repo = new Repository(); 

    public MyService() 
    { 
     repo = new Repository(); 
    } 
} 

repo будет классифицироваться как Непрозрачный Dependency потому что нет (легкий) способ изменить его, например, в тесте единицы.

Это тот же самый пример, но как Transparent Dependency:

public class MyService 
{ 
    private IRepository repo = new Repository(); 

    public MyService(IRepository repositoryDependency) 
    { 
     repo = repositoryDependency; 
    } 
} 

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

+0

Это означает, что основные недостатки приходят с Unit Test? –

2

Непрозрачная зависимость - это скрытая. Противоположностью непрозрачной зависимости является явная зависимость.

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

Непрозрачный Dependency

public class Users 
{ 
    private Database database; 

    public Users() 
    { 
     this.database = new SqlDatabase(...); 
    } 

    public User Find(int userId) 
    { 
     return database.GetById(...); 
    } 
} 

Явная зависимость

public class Users 
{ 
    private Database database; 

    public Users(Database database) 
    { 
     this.database = database; 
    } 

    public User Find(int userId) 
    { 
     return database.GetById(...); 
    } 
} 
1

Опираясь на ответ от @NikolaiDante, я хотел бы добавить аргумент, что непрозрачные зависимости могут быть введены через прозрачный.

Например:

public class MyService 
{ 
    private ISomeContext context; 

    public MyService(ISomeContext context) 
    { 
     this.context = context; 
    } 

    public void DoSomethingUseful() 
    { 
     var repository = this.context.CreateRepository<IRepository>(); 

     repository.Save(new X()); 
    } 
} 

Хотя зависимость от ISomeContext прозрачна, она скрывает тот факт, что он используется для разрешения IRepository, который я теперь рассмотрю непрозрачную зависимость. ИМХО, это уменьшает «чистоту» дизайна класса, часто в пользу удобства или лень.

Подробнее об этой проблеме вы найдете в разделе «Копание в соавторах» here.

Смежные вопросы