Design patterns 什么是不透明依赖关系?
我正在阅读有关设计模式的文章,我注意到术语“不透明依赖项”被大量使用。 一些消息来源说: 不透明依赖是一种糟糕的依赖 不透明依赖项是不能使用类的 公共API 但我不太明白 有人能给我一些使用这种依赖关系的例子吗?我为什么要避免它们?例如:Design patterns 什么是不透明依赖关系?,design-patterns,anti-patterns,Design Patterns,Anti Patterns,我正在阅读有关设计模式的文章,我注意到术语“不透明依赖项”被大量使用。 一些消息来源说: 不透明依赖是一种糟糕的依赖 不透明依赖项是不能使用类的 公共API 但我不太明白 有人能给我一些使用这种依赖关系的例子吗?我为什么要避免它们?例如: public class MyService { private IRepository repo = new Repository(); public MyService() { repo = new Reposit
public class MyService
{
private IRepository repo = new Repository();
public MyService()
{
repo = new Repository();
}
}
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());
}
}
repo
将被归类为不透明依赖项,因为没有(简单的)方法来改变它,例如在单元测试中
这是相同的示例,但作为透明依赖项:
public class MyService
{
private IRepository repo = new Repository();
public MyService(IRepository repositoryDependency)
{
repo = repositoryDependency;
}
}
在这里,我们可以传递我们自己的IRepository
并测试MyService
的行为,而DI容器之类的工具可以为我们设置依赖项,这在不透明示例中是无法实现的。例如:
public class MyService
{
private IRepository repo = new Repository();
public MyService()
{
repo = new Repository();
}
}
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());
}
}
repo
将被归类为不透明依赖项,因为没有(简单的)方法来改变它,例如在单元测试中
这是相同的示例,但作为透明依赖项:
public class MyService
{
private IRepository repo = new Repository();
public MyService(IRepository repositoryDependency)
{
repo = repositoryDependency;
}
}
在这里,我们可以传入我们自己的
IRepository
并测试MyService
的行为,而DI容器之类的工具可以为我们设置依赖项,这在不透明示例中是无法实现的。不透明依赖项是隐藏的。不透明依赖的反面是显式依赖
不透明的依赖关系是不好的,因为使用类的开发人员可能没有意识到这种依赖关系的存在。当它们调用各种方法时,可能会产生意想不到的副作用
不透明依赖项
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(...);
}
}
显式依赖关系
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(...);
}
}
不透明依赖项是隐藏的依赖项。不透明依赖的反面是显式依赖 不透明的依赖关系是不好的,因为使用类的开发人员可能没有意识到这种依赖关系的存在。当它们调用各种方法时,可能会产生意想不到的副作用 不透明依赖项
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(...);
}
}
显式依赖关系
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(...);
}
}
基于@NikolaiDante的答案,我想补充一点,即不透明依赖可以通过透明依赖引入 例如:
public class MyService
{
private IRepository repo = new Repository();
public MyService()
{
repo = new Repository();
}
}
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());
}
}
公共类MyService
{
私人语境;
公共MyService(上下文)
{
this.context=上下文;
}
公共无效dosomethingusive()
{
var repository=this.context.CreateRepository();
Save(新的X());
}
}
<>虽然,对<代码> ISOMCONTEXT/<代码>的依赖是透明的,但它隐藏了一个事实:它用于解决<代码> IRepository < /代码>,我现在认为它是不透明的依赖关系。依我看,这降低了班级设计的“纯洁性”,通常是为了方便或懒惰
在“挖掘合作者”一节中有更多关于这类问题的内容。基于@NikolaiDante的答案,我想补充一点,即不透明依赖可以通过透明依赖引入 例如:
public class MyService
{
private IRepository repo = new Repository();
public MyService()
{
repo = new Repository();
}
}
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());
}
}
公共类MyService
{
私人语境;
公共MyService(上下文)
{
this.context=上下文;
}
公共无效dosomethingusive()
{
var repository=this.context.CreateRepository();
Save(新的X());
}
}
<>虽然,对<代码> ISOMCONTEXT/<代码>的依赖是透明的,但它隐藏了一个事实:它用于解决<代码> IRepository < /代码>,我现在认为它是不透明的依赖关系。依我看,这降低了班级设计的“纯洁性”,通常是为了方便或懒惰
在“深入协作者”一节中有更多关于这类问题的内容。这意味着主要缺点来自单元测试?这意味着主要缺点来自单元测试?所有答案都给了我关键信息。现在我不确定哪一个是正确答案。所有的答案都给了我关键信息。现在我不确定哪一个是正确答案。