1200字范文,内容丰富有趣,写作的好帮手!
1200字范文 > Spring.Net学习笔记十(打造简易的依赖注入框架)

Spring.Net学习笔记十(打造简易的依赖注入框架)

时间:2019-09-21 20:43:48

相关推荐

Spring.Net学习笔记十(打造简易的依赖注入框架)

之前我们学习里一个简易的IoC框架。今天我们接着上次的程序,实现带参数构造函数对象的实例和属性的注入 。原文地址:/GoodHelper/archive//11/02/SpringNet_MyDi.html

我感觉这个很有必要对应IOC框架的理解,知道注入的工作原理,对应实际的应用是很有帮助的。

我们知道可以通过反射获取类的构造函数及参数(GetConstructors方法);可以获取属性和属性的类型(GetProperties方法)。通过Activator的CreateInstance(Type type, params object[] args)方法可以创建带参数构造函数的实例。通过SetValue方法可以给属性赋值,这样一来,我们就上次的代码稍加改造就可以实现属性的注入了。

下面是完成的代码:

publicclassPerson

{

publicstringName{get;set;}

publicintAge{get;set;}

}

publicclassPersonDao

{

privateintintProp;

publicPersonDao(intintProp)

{

this.intProp=intProp;

}

publicPersonEntity{get;set;}

publicoverridestringToString()

{

return"构造函数参数intProp为:"+this.intProp;

}

}

publicclassObjectFactory

{

privateIDictionary<string,object>objectDefine=newDictionary<string,object>();

privateObjectFactory(stringfileName)

{

InstanceObjects(fileName);//实例IoC容器

DiObjects(fileName);//属性注入

}

privatestaticObjectFactoryinstance;

privatestaticobjectlockHelper=newobject();

publicstaticObjectFactoryInstance(stringfileName)

{

if(instance==null)

{

lock(lockHelper)

{

instance=instance??newObjectFactory(fileName);

}

}

returninstance;

}

///<summary>

///实例IoC容器

///</summary>

///<paramname="fileName"></param>

privatevoidInstanceObjects(stringfileName)

{

XElementroot=XElement.Load(fileName);

varobjects=fromobjinroot.Elements("object")

selectobj;

//无参构造函数

objectDefine=objects.Where(obj=>

obj.Element("constructor-arg")==null).ToDictionary(

k=>k.Attribute("id").Value,

v=>

{

stringtypeName=v.Attribute("type").Value;

Typetype=Type.GetType(typeName);

returnActivator.CreateInstance(type);

}

);

//有参构造函数

foreach(XElementiteminobjects.Where(obj=>

obj.Element("constructor-arg")!=null))

{

stringid=item.Attribute("id").Value;

stringtypeName=item.Attribute("type").Value;

Typetype=Type.GetType(typeName);

varargs=frompropertyintype.GetConstructors()[0].GetParameters()

joinelinitem.Elements("constructor-arg")

onproperty.Nameequalsel.Attribute("name").Value

selectConvert.ChangeType(el.Attribute("value").Value,

property.ParameterType);

objectobj=Activator.CreateInstance(type,args.ToArray());

objectDefine.Add(id,obj);

}

}

///<summary>

///属性注入

///</summary>

///<paramname="fileName"></param>

privatevoidDiObjects(stringfileName)

{

XElementroot=XElement.Load(fileName);

varobjects=fromobjinroot.Elements("object")

selectobj;

foreach(KeyValuePair<string,object>iteminobjectDefine)

{

foreach(varelinobjects.Where(e=>

e.Attribute("id").Value==item.Key).Elements("property"))

{

Typetype=item.Value.GetType();

//获取属性

foreach(PropertyInfopropertyintype.GetProperties())

{

if(property.Name==el.Attribute("name").Value)

{

if(el.Attribute("value")!=null)

{

//设置属性值

property.SetValue(item.Value,

Convert.ChangeType(el.Attribute("value").Value,

property.PropertyType),null);

}

elseif(el.Attribute("ref")!=null)

{

objectrefObject=null;

if(objectDefine.ContainsKey(el.Attribute("ref").Value))

{

refObject=objectDefine[el.Attribute("ref").Value];

}

//设置关联对象属性

property.SetValue(item.Value,refObject,null);

}

}

}

}

}

}

///<summary>

///获取对象

///</summary>

///<paramname="id"></param>

///<returns></returns>

publicobjectGetObject(stringid)

{

objectresult=null;

if(objectDefine.ContainsKey(id))

{

result=objectDefine[id];

}

returnresult;

}

} <?xmlversion="1.0"encoding="utf-8"?>

<objects>

<objectid="person"type="SpringNetMyDi.Person,SpringNetMyDi">

<!--属性值类型注入-->

<propertyname="Name"value="LiuDong"/>

<propertyname="Age"value="27"/>

</object>

<objectid="personDao"type="SpringNetMyDi.PersonDao,SpringNetMyDi">

<!--构造器注入-->

<constructor-argname="intProp"value="1"/>

<propertyname="Entity"ref="person"/>

</object>

</objects> classProgram

{

staticvoidMain(string[]args)

{

ObjectFactoryfactory=ObjectFactory.Instance(@"F:\Exercise\SpringNet\Step1\SpringNet_Lesson9\SpringNetMyDi\Objects.xml");

PersonDaodao=(PersonDao)factory.GetObject("personDao");

Console.WriteLine("姓名:"+dao.Entity.Name);

Console.WriteLine("年龄:"+dao.Entity.Age);

Console.WriteLine(dao);

Console.ReadLine();

}

}

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。