The IOC (inverse of control) can be translated as "controlled inversion", but most people are accustomed to calling it "dependency injection". In spring, the implementation class, parameter information, etc. can be configured in the corresponding configuration file by IOC, so when the implementation class or parameter information needs to be changed, only the configuration file needs to be modified, and this method further reduces the coupling between the class and the class on the basis of the above example. We can also inject other objects needed by an object, which is done in the configuration file, and the spring IOC implementation principle leverages the Java reflection mechanism, and spring acts as a factory, and we don't need to build our own factory class. The Spring factory class will help us to read the configuration files, inject objects using the reflection mechanism, and we can get the corresponding objects by the name of the bean. Let's take a look at the following simulation of spring's Bean factory class:
Packageorg.amigo.reflection;ImportJava.io.InputStream;ImportJava.lang.reflect.Method;ImportJava.util.HashMap;ImportJava.util.Iterator;ImportJava.util.Map;ImportOrg.dom4j.Attribute;Importorg.dom4j.Document;Importorg.dom4j.Element;ImportOrg.dom4j.io.SAXReader;/*** Bean factory class. */ Public classBeanfactory {Privatemap<string, object> beanmap =NewHashmap<string, object>(); /*** Initialization of the Bean factory. * @paramXML XML configuration file*/ Public voidinit (String xml) {Try { //reads the specified configuration fileSaxreader reader =NewSaxreader (); ClassLoader ClassLoader=Thread.CurrentThread (). Getcontextclassloader (); //get the specified XML file from the class directoryInputStream ins =classloader.getresourceasstream (XML); Document Doc=reader.read (INS); Element Root=doc.getrootelement (); Element foo; //traversing Beans for(Iterator i = root.elementiterator ("Bean"); I.hasnext ();) {Foo=(Element) i.next (); //gets the Bean's property ID and ClassAttribute id = foo.attribute ("id"); Attribute CLS= Foo.attribute ("Class"); //Use the Java reflection mechanism to get the class object through the name of ClassClass Bean =Class.forName (Cls.gettext ()); //get information for the corresponding classJava.beans.BeanInfo info =Java.beans.Introspector.getBeanInfo (Bean); //gets its property descriptionJava.beans.PropertyDescriptor pd[] =info.getpropertydescriptors (); //ways to set valuesMethod MSet =NULL; //Create an ObjectObject obj =bean.newinstance (); //iterate over the property properties of the Bean for(Iterator ite = Foo.elementiterator ("property")); Ite.hasnext ();) {Element Foo2=(Element) ite.next (); //gets the property's name attributeAttribute name = Foo2.attribute ("name"); String value=NULL; //gets the value of the property's child element, value for(Iterator ite1 = Foo2.elementiterator ("value")); Ite1.hasnext ();) {Element node=(Element) ite1.next (); Value=Node.gettext (); Break; } for(intk = 0; K < Pd.length; k++) { if(Pd[k].getname (). Equalsignorecase (Name.gettext ())) {MSet=Pd[k].getwritemethod (); //use Java's reflection to call a set method of an object and set the value inmset.invoke (obj, value); } } } < /c4>//put the object in Beanmap, where key is the ID value and value is the objectBeanmap.put (Id.gettext (), obj); } } Catch(Exception e) {System.out.println (e.tostring ()); } } /*** Gets the Bean object from the bean's ID. * @paramBeanname Bean's ID *@returnreturns the corresponding object*/ PublicObject Getbean (String beanname) {Object obj=Beanmap.get (beanname); returnobj; } /*** Test method. * @paramargs*/ Public Static voidMain (string[] args) {Beanfactory factory=Newbeanfactory (); Factory.init ("Config +"); JavaBean JavaBean= (JavaBean) factory.getbean ("JavaBean"); System.out.println ("Username=" +javabean.getusername ()); System.out.println ("Password=" +Javabean.getpassword ()); }}
the init (XML) method of the class, which injects properties into the object through the specified XML , and in order to test the class, I also need to create a new JavaBean and create a new configuration file named. config in the SRC directory. The contents of JavaBean are as follows:
Packageorg.amigo.reflection;/*** * Simple bean for testing*/ Public classJavaBean {PrivateString UserName; PrivateString password; PublicString GetPassword () {returnpassword; } PublicString GetUserName () {returnUserName; } Public voidsetusername (String userName) { This. UserName =UserName; } Public voidSetPassword (String password) { This. Password =password; }}
There are two properties in this simple Bean object, username and password respectively, and we inject the corresponding property values into the configuration file CONFIG. The contents of the configuration file are as follows:
<?XML version= "1.0" encoding= "UTF-8"?><Beans> <BeanID= "JavaBean"class= "Org.amigo.reflection.JavaBean"> < Propertyname= "UserName"> <value>A Honey fruit</value> </ Property> < Propertyname= "Password"> <value>12345678</value> </ Property> </Bean></Beans>
after the class and configuration files are complete, you can run the Beanfactory.java file and the console displays the following:username= Pistachio password=12345678as you can see, although there is no property assignment in the main () method, the attribute value has been injected, class Bean in the Beanfactory class = Class.forName (Cls.gettext ()), and the class name is used to obtain the corresponding class. Mset.invoke (obj, value); The method of invoking specific objects through the Invoke method is implemented based on the Java reflection mechanism, where we once witnessed the power of the Java reflection mechanism. This is, of course, a simple demonstration of the IOC, which is much more complex in spring, for example, a bean can reference another bean, can have multiple configuration files, load configuration files in multiple ways, and so on. But the principle still uses the Java reflection mechanism to realize the IOC.
Four.
in this paper, the author describes the Java Reflection Mechanism Overview and preliminary discussion, IOC use of the background, IOC, etc., demonstrating the power of the Java Reflection Mechanism API, and by writing its own simple IOC framework, so that readers better understand the IOC implementation principle. through a brief implementation example of IOC, this paper simulates the implementation of IOC in spring, although it only completes a small part of the work of dependency injection in spring, but it shows the application of the Java reflection mechanism in spring very well. will enable us to better understand the principles of the IOC implementation, but also for us to implement their own quasi-Spring framework provides
Java Reflection mechanism detailed (3)-java reflection and proxy implementation IOC mode simulation spring