当第一次遇到控制反转(IoC)时,它可能非常令人困惑。

这是怎么一回事?它解决了哪个问题?什么时候使用合适,什么时候不合适?


当前回答

什么是控制反转?

如果您遵循这两个简单的步骤,您就完成了控制反转:

把该做什么和什么时候该做分开。确保零件何时尽可能少地了解什么零件;反之亦然。

根据您用于实现的技术/语言,这些步骤中的每一个都有几种可能的技术。

--

控制反转(IoC)的反转部分令人困惑;因为反转是相对项。了解IoC的最好方法是忘记这个词!

--

示例

事件处理。事件处理程序(做什么部分)--引发事件(何时做部分)依赖注入。构造依赖项(做什么部分)的代码——在需要时为客户机实例化和注入依赖项,这通常由Dagger等DI工具来处理(什么时候做部分)。接口。组件客户端(何时执行部分)--组件接口实现(执行部分)x装置夹具。Setup和TearDown(要做的部分)--xUnit框架在开始时调用Setup,在结束时调用TearDown(何时做部分)模板方法设计模式。模板方法何时执行部分--基本子类实现何时执行部分COM.DllMain、DllCanUnload等中的DLL容器方法(做什么部分)--COM/OS(什么时候做部分)

其他回答

假设你是一个物体。然后你去餐馆:

没有IoC:你要求“苹果”,当你要求更多时,你总是得到苹果。

与IoC:你可以要求“水果”。每次上桌你都可以得到不同的水果。例如,苹果、橙子或西瓜。

所以,很明显,当你喜欢品种时,IoC是首选。

我将写下我对这两个术语的简单理解:

For quick understanding just read examples*

依赖注入(DI):依赖注入通常意味着将方法依赖的对象作为参数传递给方法,而不是让方法创建依赖对象。这在实践中意味着,该方法不直接依赖于特定的实现;任何满足要求的实现都可以作为参数传递。使用此对象可以告诉它们的依赖关系。春天使它成为可能。这导致了松散耦合的应用程序开发。

Quick Example:EMPLOYEE OBJECT WHEN CREATED,
              IT WILL AUTOMATICALLY CREATE ADDRESS OBJECT
   (if address is defines as dependency by Employee object)

控制反转(IoC)容器:这是框架的共同特征,IOC通过其BeanFactory管理java对象——从实例化到销毁-由IoC容器实例化的Java组件称为bean,IoC容器管理bean的范围、生命周期事件以及为其配置和编码的任何AOP特性。

快速示例:控制反转是指获得自由、更大的灵活性和更少的依赖性。当你使用台式电脑时,你是从属的(或者说,受控的)。你必须坐在屏幕前看着屏幕。用键盘打字,用鼠标导航。一个糟糕的书面软件会让你更加痛苦。如果你用笔记本电脑取代了你的桌面,那么你的控制就有点颠倒了。你可以轻松地拿着它四处走动。所以现在你可以用电脑控制你的位置,而不是电脑控制它。

通过实现控制反转,软件/对象消费者可以获得更多的软件/对象控制/选项,而不是被控制或拥有更少的选项。

作为设计指南的控制反转具有以下目的:

某个任务的执行与实现是分离的。每个模块都可以专注于它的设计目的。模块不假设其他系统做什么,而是依赖它们的合同。替换模块对其他模块没有任何副作用,我将在这里保持抽象,您可以访问以下链接以详细了解主题。一个很好的例子

详细说明

假设我们在酒店开会。

我们邀请了很多人,所以我们漏掉了很多壶水和很多塑料杯。

当有人想喝水时,他/她将杯子装满,喝水,然后将杯子扔在地板上。

大约一个小时后,我们的地板上覆盖着塑料杯和水。

让我们在反转控件后尝试:

想象一下,在同一地点举行同一次会议,但我们现在有一个服务员只带一个玻璃杯,而不是塑料杯(Singleton)

当有人想喝酒时,服务员会给他们一杯。他们把它喝了,然后还给服务员。

抛开卫生问题不谈,使用服务员(过程控制)更有效、更经济。

这正是Spring(另一个IoC容器,例如:Guice)所做的。Spring IoC没有让应用程序使用新的关键字(例如,拿一个塑料杯子)创建所需的东西,而是为应用程序提供所需对象(一杯水)的同一杯子/实例(singleton)。

把自己想象成这样一个会议的组织者:

示例:-

public class MeetingMember {

    private GlassOfWater glassOfWater;

    ...

    public void setGlassOfWater(GlassOfWater glassOfWater){
        this.glassOfWater = glassOfWater;
    }
    //your glassOfWater object initialized and ready to use...
    //spring IoC  called setGlassOfWater method itself in order to
    //offer to meetingMember glassOfWater instance

}

有用的链接:-

http://adfjsf.blogspot.in/2008/05/inversion-of-control.htmlhttp://martinfowler.com/articles/injection.htmlhttp://www.shawn-barrett.com/blog/post/Tip-of-the-day-e28093-Inversion-Of-Control.aspx

控制反转,(或IoC),是关于获得自由(你结婚了,失去了自由,你被控制了。你离婚了,你刚刚实现了控制反转。这就是我们所说的“脱钩”。好的计算机系统阻碍了一些非常亲密的关系。)更灵活(你办公室的厨房只供应干净的自来水,这是你想喝水时的唯一选择。你的老板通过安装一台新的咖啡机实现了控制反转。现在你可以灵活选择自来水或咖啡。)和更少的依赖性(你的伴侣有工作,你没有工作,你在经济上依赖你的伴侣,所以你受到控制。你找到了工作,你实现了控制反转。良好的计算机系统鼓励依赖。)

当你使用台式电脑时,你已经从(或者说,被控制)了。你必须坐在屏幕前看着屏幕。用键盘打字,用鼠标导航。一个写得不好的软件会让你更加痛苦。如果你把桌面换成笔记本电脑,那么你的控制就有点颠倒了。你可以轻松地拿着它四处走动。所以现在你可以用电脑控制你的位置,而不是由电脑控制。

通过实现控制反转,软件/对象消费者可以获得更多的软件/对象控制/选项,而不是被控制或拥有更少的选项。

考虑到上述想法。我们仍然错过了IoC的一个关键部分。在IoC的场景中,软件/对象使用者是一个复杂的框架。这意味着您创建的代码不是自己调用的。现在让我们来解释一下为什么这种方式对web应用程序更有效。

假设您的代码是一组工作人员。他们需要造一辆车。这些工人需要一个地方和工具(软件框架)来制造汽车。一个传统的软件框架就像一个有很多工具的车库。因此,工人们需要自己制定计划,并使用工具来制造汽车。造一辆车不是一件容易的事,工人们很难做好计划并进行适当的合作。一个现代化的软件框架将像一个拥有所有设施和管理人员的现代化汽车工厂。工人不必制定任何计划,管理者(框架的一部分,他们是最聪明的人,制定了最复杂的计划)将帮助协调,以便工人知道何时完成他们的工作(框架调用您的代码)。工人们只需要足够灵活地使用经理给他们的任何工具(通过使用依赖注入)。

尽管工人将项目管理的控制权交给了管理者(框架)。但有一些专业人士帮助是很好的。这就是IoC的真正来源。

具有MVC架构的现代Web应用程序依赖于框架来执行URL路由,并将控制器放置在适当的位置以供框架调用。

依赖注入和控制反转是相关的。依赖注入在微观层面,控制反转在宏观层面。为了完成一顿饭(实现IoC),你必须吃每一口(实现DI)。

我觉得用这么多先前的答案回答这个问题有点尴尬,但我只是觉得任何答案都没有足够简单地说明这个概念。

所以我们开始。。。

在非IOC应用程序中,您需要对流程进行编码,并在其中包含所有详细步骤。考虑一个创建报告的程序,它将包含设置打印机连接、打印页眉、遍历详细记录、打印页脚、可能执行页面馈送等的代码。

在IOC版本的报告程序中,您将配置一个通用的、可重用的报告类的实例,即一个包含打印报告的过程流但其中没有任何详细信息的类。您提供的配置可能使用DI来指定报告应该调用哪个类来打印标题、报告应该调用什么类来打印详细信息行、,以及Report应该调用什么类来打印页脚。

因此,控制反转来自控制过程,而不是代码,而是包含在一个外部的、可重用的类(Report)中,该类允许您指定或注入(通过DI)报告的详细信息-页眉、详细信息行和页脚。

通过提供不同的细节类集,可以使用同一Report类(控制类)生成任意数量的不同报告。您通过依赖Report类来提供控件,而只是通过注入来指定报表之间的差异,从而实现了控件的反转。

在某些方面,IOC可以与驱动器备份应用程序相比较-备份总是执行相同的步骤,但备份的文件集可能完全不同。

现在具体地回答最初的问题。。。

这是怎么一回事?IOC依赖于一个可重用的控制器类,并提供针对当前问题的详细信息。它解决了哪个问题?防止您必须重述控制流程。什么时候使用合适,什么时候不合适?无论何时创建控制流始终相同且仅更改细节的流程流。在创建一次性自定义流程时,您不会使用它。

最后,IOC不是DI,DI也不是IOC——DI通常可以在IOC中使用(为了说明抽象控制类的细节)。

无论如何,我希望这有帮助。