Spring.Core IoC(一)

Spring.Core提供了基本的反转控制容器。其中要提到两个接口:IObjectFactory, IApplicationContext。IObjectFactory提供配置机制。IApplicationContext建立在IObjectFactory之上,并且加入了其他功能,如:AOP,消息资源处理,事件传播和应用层上下文。

当IApplicationContext加入了很多企业级方法时,IObjectFactory提供配置框架和基本方法。IApplicationContext是一个IObjectFactory的超集。

下面举个简单的例子看看:

我们使用Spring.Net的注入功能实现一个电影查找程序:

image

开始:

首先,在项目中引用Spring.Core,添加配置文件:

<configSections>

<sectionGroup name="spring">

<section name="context" type="Spring.Context.Support.ContextHandler, Spring.Core"/>

<section name="objects" type="Spring.Context.Support.DefaultSectionHandler, Spring.Core"/>

</sectionGroup>

</configSections>

<spring>

<context>

<resource uri="config://spring/objects" />

</context>

<objects xmlns="http://www.springframework.net">

<description>An example that demonstrates simple Ioc features.</description>

</objects>

</spring>

在Main函数中加入:

IApplicationContext ctx = ContextRegistry.GetContext();

对象定义:

加入一个MovieLister的类型:

public class MovieLister

{

    private IMovieFinder _movieFinder;

    public IMovieFinder MovieFinder

    {

        set

        {

            _movieFinder = value;

        }

    }

    public Movie[] MoviesDirectedBy(string director)

    {

        IList allMovies = _movieFinder.FindAll();

        IList movies = new ArrayList();

        foreach (Movie m in allMovies)

        {

            if (director.Equals(m.Director))

            {

                movies.Add(m);

            }

        }

        return (Movie[])ArrayList.Adapter(movies).ToArray(typeof(Movie));

    }

}

在配置文件中编写:

<object name="MyMovieLister" type="Spring.Examples.MovieFinder.MovieLister, Spring.Examples.MovieFinder"></object>

其中要注意,name是唯一的。接下来在使用IApplicationContext引用MovieLister对象,代码如下:

MovieLister lister = (MovieLister)ctx.GetObject("MyMovieLister");

在MovieLister类型中定义了IMovieFinder,接下来我们就加入IMovieFinder和SampleMovieFinder,然后配置他们。

public interface IMovieFinder

{

      list FindAll();

}

public class SimpleMovieFinder : IMovieFinder

{

      private ArrayList _list = new ArrayList();

      public SimpleMovieFinder()

      {

            InitList();

      }

      public void AddMovie(Movie m)

      {

            _list.Add(m);

      }

      private void InitList()

      {

            _list.Add(new Movie("La vita e bella", "Roberto Benigni"));

      }

      public IList FindAll()

      {

            return new ArrayList(_list);

      }

}

配置文件中添加一个对象:

<object name="MyMovieFinder" type="Spring.Examples.MovieFinder.SimpleMovieFinder, Spring.Examples.MovieFinder"></object>

设置注入:

如何把MyMovieFinder注入到MovieLister中的IMovieFinder对象中,修改配置文件,在MyMovieLister中加入属性:

<object name="MyMovieLister" type="Spring.Examples.MovieFinder.MovieLister, Spring.Examples.MovieFinder">

<property name="movieFinder" ref="AnotherMovieFinder" />

</object>

在应用程序中,当MyMovieLister对象从IApplicationContext中被找到,Spring.Net IoC容器将MyMovieFinder对象注入到MovieLister对象的MovieFinder属性中。

现在来列出电影的导演:

static void Main(string[] args)

{

      try

      {

            IApplicationContext ctx = ContextRegistry.GetContext();

            MovieLister lister = (MovieLister)ctx.GetObject("MyMovieLister");

            Movie[] movies = lister.MoviesDirectedBy("Roberto Benigni");

            foreach (Movie movie in movies)

            {

                  Console.WriteLine(string.Format("Movie Title = '{0}', Director = '{1}'.",

                  movie.Title, movie.Director));

            }

      }

      catch (Exception ex)

      {

            Console.WriteLine(ex.Message);

      }

      Console.Read();

}

运行结果如下:

Movie Title = 'La vita e bella', Director = 'Roberto Benigni'.

构造函数注入

现在在应用程序的配置文件中定义另一个IMovieFinder

<object name="AnotherMovieFinder" type="Spring.Examples.MovieFinder.ColonDelimitedMovieFinder, Spring.Examples.MovieFinder"></object>

ColonDelimitedMovieFinder的代码如下:

public class ColonDelimitedMovieFinder : IMovieFinder

{

      private FileInfo _movieFile;

      private IList _movies;

      private static readonly char[] Delimeter = new char[] { ':' };

      public ColonDelimitedMovieFinder(FileInfo file)

      {

            MovieFile = file;

      }

      public FileInfo MovieFile

      {

            get

            {

                  return _movieFile;

            }

            set

            {

                  _movieFile = value;

                  if (_movieFile != null && _movieFile.Exists)

                  {

                        InitList();

                  }

            }

      }

      public IList FindAll()

      {

            return _movies;

      }

      private void InitList()

      {

            _movies = new ArrayList();

            using (StreamReader reader = MovieFile.OpenText())

            {

                  string line = null;

                  while ((line = reader.ReadLine()) != null)

                  {

                        string[] tuple = line.Split(Delimeter);

                        Movie movie = new Movie(tuple[0], tuple[1]);

                        _movies.Add(movie);

                  }

            }

      }

}

这时候应用程序运行

IMovieFinder finder = (IMovieFinder)ctx.GetObject("ColonDelimitedMovieFinder");

但是运行后会出现Spring.Objects.Factory.ObjectCreationException异常。因为ColonDelimitedMovieFinder没有无参数的构造函数。在配置文件中加入参数配置。

<object name="AnotherMovieFinder" type="Spring.Examples.MovieFinder.ColonDelimitedMovieFinder, Spring.Examples.MovieFinder">

<constructor-arg index="0" value="movies.txt"/>

</object>

运行结果为:

image

源代码下载:
/Files/kid-li/ConsoleIoCStudy.rar

posted @ 2008-04-03 15:12  KiddLee  Views(4284)  Comments(9Edit  收藏  举报