FreshMvvm 中的控制反转 (IOC)
Inversion of Control (IOC) in FreshMvvm
关于IOC,我看了下面的定义和注册interface
,我真的看不懂
We don’t need to include our own IOC container, FreshMvvm comes with a
IOC container built-in. It’s using TinyIOC underneath, but with
different naming to avoid conflicts.
与 FreshIOC 的接口注册,如果您看到此代码,在应用程序启动时进行此实现
public App()
{
InitializeComponent();
//Interface rgistration with FreshIOC
FreshIOC.Container.Register<IContactRepository, ContactRepository>();
FreshIOC.Container.Register<IValidator, ContactValidator>();
//var mainPage = FreshPageModelResolver.ResolvePageModel<AddContactPageModel>();
//MainPage = new FreshNavigationContainer(mainPage);
}
为什么我们需要注册接口,如果不注册那么它的真正实现是什么?实施这个原则有什么好处吗? This 我关注的文章。
内置的IOC容器是TinyIOC的抽象。
通过 FreshMvvm 抽象在 TinyIOC 容器中注册一个类型:
FreshIOC.Container.Register<ISomeInterface, SomeImplementation>();
稍后使用它:
// Gets object of type SomeImplementation
var instanceOfConcreteType = FreshIOC.Container.Resolve<ISomeInterface>();
这是 post 讨论什么是 IOC :What is Inversion of Control?
如果您在 Xamarin.Forms 中使用过 DependencySerices,那么您已经使用了大部分。从Xamarin.Forms
的角度来解释
假设您的 ContentPage
需要 Network
class 来检查是否存在网络连接,传统的方法是使用 new
关键字并获取实例,以便您可以调用它的方法。
public MyContentPage : ContentPage
{
private Network network;
public MyContentPage()
{
//..
network = new Network();
}
}
public Network()
{
public bool HasConnectivity() { ... }
}
这没有错,但是如果Network
class里面需要一个Log
class怎么办?而MyContentPage
还需要Log
class和一个Dialog
class?这需要在所有其他 50 页中完成?依赖注入解决了这些问题以及更多问题!
您创建接口及其实现,然后将它们注册到容器中。然后容器为你解决所有的依赖关系!
public MyContentPage : ContentPage
{
private INetwork _network;
private IDialog _dialog;
public MyContentPage(INetwork network, IDialog dialog)
{
//..
_network = network;
_dialog = dialog;
}
}
public Network(ILog log)
{
public bool HasConnectivity() { ... }
}
如果您已经注册了所有依赖项,Container 将处理依赖关系图并为您解决它们。如果容器无法解析图表,可能是因为您没有注册或可能是循环依赖,它会抛出异常。
一开始这似乎完全没有必要,但随着您的应用程序的增长,MVVM 与 DI 相结合会变得更强大并且更容易开发。
我所解释的只是DI的一小部分,你可以在这个awesome Martin Fowler post
中阅读更多关于IoC和DI的内容
关于IOC,我看了下面的定义和注册interface
,我真的看不懂
We don’t need to include our own IOC container, FreshMvvm comes with a IOC container built-in. It’s using TinyIOC underneath, but with different naming to avoid conflicts.
与 FreshIOC 的接口注册,如果您看到此代码,在应用程序启动时进行此实现
public App()
{
InitializeComponent();
//Interface rgistration with FreshIOC
FreshIOC.Container.Register<IContactRepository, ContactRepository>();
FreshIOC.Container.Register<IValidator, ContactValidator>();
//var mainPage = FreshPageModelResolver.ResolvePageModel<AddContactPageModel>();
//MainPage = new FreshNavigationContainer(mainPage);
}
为什么我们需要注册接口,如果不注册那么它的真正实现是什么?实施这个原则有什么好处吗? This 我关注的文章。
内置的IOC容器是TinyIOC的抽象。
通过 FreshMvvm 抽象在 TinyIOC 容器中注册一个类型:
FreshIOC.Container.Register<ISomeInterface, SomeImplementation>();
稍后使用它:
// Gets object of type SomeImplementation
var instanceOfConcreteType = FreshIOC.Container.Resolve<ISomeInterface>();
这是 post 讨论什么是 IOC :What is Inversion of Control?
如果您在 Xamarin.Forms 中使用过 DependencySerices,那么您已经使用了大部分。从Xamarin.Forms
的角度来解释假设您的 ContentPage
需要 Network
class 来检查是否存在网络连接,传统的方法是使用 new
关键字并获取实例,以便您可以调用它的方法。
public MyContentPage : ContentPage
{
private Network network;
public MyContentPage()
{
//..
network = new Network();
}
}
public Network()
{
public bool HasConnectivity() { ... }
}
这没有错,但是如果Network
class里面需要一个Log
class怎么办?而MyContentPage
还需要Log
class和一个Dialog
class?这需要在所有其他 50 页中完成?依赖注入解决了这些问题以及更多问题!
您创建接口及其实现,然后将它们注册到容器中。然后容器为你解决所有的依赖关系!
public MyContentPage : ContentPage
{
private INetwork _network;
private IDialog _dialog;
public MyContentPage(INetwork network, IDialog dialog)
{
//..
_network = network;
_dialog = dialog;
}
}
public Network(ILog log)
{
public bool HasConnectivity() { ... }
}
如果您已经注册了所有依赖项,Container 将处理依赖关系图并为您解决它们。如果容器无法解析图表,可能是因为您没有注册或可能是循环依赖,它会抛出异常。
一开始这似乎完全没有必要,但随着您的应用程序的增长,MVVM 与 DI 相结合会变得更强大并且更容易开发。
我所解释的只是DI的一小部分,你可以在这个awesome Martin Fowler post
中阅读更多关于IoC和DI的内容