1.spring入门,xml创建对象
配置文件
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
https://www.springframework.org/schema/beans/spring-beans.xsd">
<bean id="car1" class="com.shxp.pojo.Car">
<property name="brind" value="奥迪A6L"></property>
<property name="price" value="45.6"></property>
<property name="color" value="red"></property>
</bean>
</beans>
pojo对象
package com.shxp.pojo;
public class Car {
/*品牌*/
private String brind;
/*价格*/
private double price;
/*颜色*/
private String color;
public String getBrind() {
return brind;
}
public void setBrind(String brind) {
this.brind = brind;
}
public double getPrice() {
return price;
}
public void setPrice(double price) {
this.price = price;
}
public String getColor() {
return color;
}
public void setColor(String color) {
this.color = color;
}
@Override
public String toString() {
return "Car{" +
"brind='" + brind + '\'' +
", price=" + price +
", color='" + color + '\'' +
'}';
}
}
测试类
package com.shxp.pojo;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class CarTest {
public static void main(String[] args) {
ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml");
Car car = (Car) context.getBean("car1");
System.out.println(car.toString());
}
}
2.IOC创建对象的4种方式
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
https://www.springframework.org/schema/beans/spring-beans.xsd">
<!--1.无参构造-->
<!--<bean id="car1" class="com.shxp.pojo.Car">
<property name="brind" value="奥迪A6L"></property>
<property name="price" value="45.6"></property>
<property name="color" value="red"></property>
</bean>-->
<!--2.用下标注入-->
<bean id="car2" class="com.shxp.pojo.Car">
<constructor-arg index="0" value="宝马X5"></constructor-arg>
<constructor-arg index="1" value="16.7"></constructor-arg>
<constructor-arg index="2" value="black"></constructor-arg>
</bean>
<!--3.用类型注入-->
<bean id="car3" class="com.shxp.pojo.Car">
<constructor-arg name="brind" value="现代"></constructor-arg>
<constructor-arg name="color" value="black"></constructor-arg>
<constructor-arg name="price" value="46.2"></constructor-arg>
</bean>
<bean id="car4" class="com.shxp.pojo.Car">
<constructor-arg type="java.lang.String" value="奥迪"></constructor-arg>
<constructor-arg type="double" value="46.2"></constructor-arg>
<constructor-arg type="java.lang.String" value="1"></constructor-arg>
</bean>
</beans>
3.Spring配置
1.beans外层标签
2.创建对象标签
3.alias别名标签,可以重命名bean,但bean的name属性也可以重命名而且比alias更加强大,可以重命名多个名字
4.import 可以引入其他配置文件
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
https://www.springframework.org/schema/beans/spring-beans.xsd">
<bean id="car7" class="com.shxp.pojo.Car">
<constructor-arg index="0" value="宝马X5"></constructor-arg>
<constructor-arg index="1" value="16.7"></constructor-arg>
<constructor-arg index="2" value="black"></constructor-arg>
</bean>
<bean id="chenglong" class="com.shxp.pojo.Person">
<!--第一种普通注入-->
<property name="name">
<value>成龙</value>
</property>
<property name="phonenumber" value="1383838438"></property>
<property name="car" ref="car7"></property>
<!--第二种list对象注入-->
<property name="carList">
<list>
<ref bean="car"></ref>
<ref bean="car2"></ref>
<ref bean="car3"></ref>
<ref bean="car4"></ref>
</list>
</property>
<!--第三种map注入-->
<property name="map">
<map>
<entry key="wife" value="范冰冰"></entry>
</map>
</property>
<!--第四种数组注入-->
<property name="likebooks">
<array>
<value>1</value>
<value>2</value>
<value>3</value>
<value>4</value>
<value>5</value>
</array>
</property>
</bean>
</beans>
4.c命名和p命名空间注入
使用c和p都可以向bean注入值,但使用p必须由无参构造,使用c要有有参构造
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:p="http://www.springframework.org/schema/p"
xmlns:c="http://www.springframework.org/schema/c"
xsi:schemaLocation="http://www.springframework.org/schema/beans
https://www.springframework.org/schema/beans/spring-beans.xsd">
<bean class="com.shxp.pojo.Person" id="car6" p:name="das"></bean>
<bean class="com.shxp.pojo.Car" id="car8" c:brind="奥迪" p:color="123" c:price="123"></bean>
</beans>
5.Spring的自动装配
Spriing的自动装配有两种:
1.byName装配:根据对象set方法的参数名字取配置文件里搜索。名字一致的则自动装配。
2.byType装配:根据参数类型进行自动装配,但要保证全局只有一个此类型的参数
byname注入
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:p="http://www.springframework.org/schema/p"
xmlns:c="http://www.springframework.org/schema/c"
xsi:schemaLocation="http://www.springframework.org/schema/beans
https://www.springframework.org/schema/beans/spring-beans.xsd">
<bean id="car" class="com.shxp.pojo.Car">
<property name="brind" value="宝马"></property>
<property name="price" value="45.5"></property>
<property name="color" value="红色"></property>
</bean>
<bean id="person1" class="com.shxp.pojo.Person" autowire="byName">
</bean>
</beans>
byType注入
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:p="http://www.springframework.org/schema/p"
xmlns:c="http://www.springframework.org/schema/c"
xsi:schemaLocation="http://www.springframework.org/schema/beans
https://www.springframework.org/schema/beans/spring-beans.xsd">
<bean id="car" class="com.shxp.pojo.Car">
<property name="brind" value="宝马"></property>
<property name="price" value="45.5"></property>
<property name="color" value="红色"></property>
</bean>
<bean id="person1" class="com.shxp.pojo.Person" autowire="byType">
</bean>
</beans>
6.注解实现自动装配
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:p="http://www.springframework.org/schema/p"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:c="http://www.springframework.org/schema/c"
xsi:schemaLocation="http://www.springframework.org/schema/beans
https://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
https://www.springframework.org/schema/context/spring-context.xsd">
<context:annotation-config></context:annotation-config>
<bean id="dog1" class="com.shxp.autowire.Dog" p:name="小猫"></bean>
<bean id="dog2" class="com.shxp.autowire.Dog" p:name="小猫"></bean>
<bean id="cat1" class="com.shxp.autowire.Cat" p:name="小狗"></bean>
<bean id="cat2" class="com.shxp.autowire.Cat" p:name="小狗"></bean>
<bean id="person" class="com.shxp.autowire.Person"></bean>
</beans>
@Autowired,@Qualifier组合注解
package com.shxp.autowire;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import javax.annotation.Resource;
public class Person {
@Autowired
@Qualifier(value = "cat1")
private Cat cat;
@Qualifier(value = "dog1")
@Autowired
private Dog dog;
public Cat getCat() {
return cat;
}
public void setCat(Cat cat) {
this.cat = cat;
}
public Dog getDog() {
return dog;
}
public void setDog(Dog dog) {
this.dog = dog;
}
@Override
public String toString() {
return "Person{" +
"cat=" + cat.toString() +
", dog=" + dog.toString() +
'}';
}
}
使用Resource注解
package com.shxp.autowire;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import javax.annotation.Resource;
public class Person {
@Resource(name = "cat1")
private Cat cat;
@Resource(name = "dog1")
private Dog dog;
public Cat getCat() {
return cat;
}
public void setCat(Cat cat) {
this.cat = cat;
}
public Dog getDog() {
return dog;
}
public void setDog(Dog dog) {
this.dog = dog;
}
@Override
public String toString() {
return "Person{" +
"cat=" + cat.toString() +
", dog=" + dog.toString() +
'}';
}
}
@Resource与 @Autowired注解的区别
1.都是用来装配的,都可以直接放在属性上。
2.@Autowired是使用byType实现的,而且必须要求这个对象存在。
3.@Resource默认是使用ByName实现的,如果byName找不到就会使用byType去实现。两个都找不到就报错。
7.使用javaconfig实现配置
1.实体类
package com.shxp.pojo;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.stereotype.Component;
@Component
public class Car {
/*品牌*/
//@Value("奥迪")
private String brind;
/*价格*/
//@Value("45.6")
private double price;
/*颜色*/
//@Value("红色")
private String color;
public String getBrind() {
return brind;
}
public void setBrind(String brind) {
this.brind = brind;
}
public double getPrice() {
return price;
}
public void setPrice(double price) {
this.price = price;
}
public String getColor() {
return color;
}
public void setColor(String color) {
this.color = color;
}
public Car(String brind, double price, String color) {
this.brind = brind;
this.price = price;
this.color = color;
}
public Car() {
super();
}
@Override
public String toString() {
return "Car{" +
"brind='" + brind + '\'' +
", price=" + price +
", color='" + color + '\'' +
'}';
}
}
配置类
package com.shxp.pojo;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
@Configuration
public class Configurtion {
@Bean
public Car getcar(){
return new Car("宝马",45.6,"黑色");
}
}
测试类
package com.shxp.pojo;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import org.springframework.context.annotation.Configuration;
public class CarTest1 {
public static void main(String[] args) {
ApplicationContext context = new AnnotationConfigApplicationContext(Configurtion.class);
Car car = (Car) context.getBean("getcar");
System.out.println(car);
}
}
@Component在类上加入此注解说明已经被Spring接管
@@Configuration在类上加入此注解说明此类事一个配置类
7.静态代理模式举例
现在有一套完整的crud,因业务需求增加一套日志系统。在不改变原有代码的基础上如何实现业务?
1.被代理虚拟对象
package com.shxp.aop;
public interface CrudDao {
void add();
void delete();
void update();
void query();
}
2.被代理的真是对象
package com.shxp.aop;
public class Crudimpl implements CrudDao{
public void add() {
System.out.println("添加方法已执行");
}
public void delete() {
System.out.println("删除方法已执行");
}
public void update() {
System.out.println("修改方法已执行");
}
public void query() {
System.out.println("查询方法已执行");
}
}
3.代理对象
package com.shxp.aop;
public class Crudservice implements CrudDao{
private Crudimpl crudimpl;
public Crudservice(Crudimpl crudimpl1){
this.crudimpl=crudimpl1;
}
public void add() {
crudimpl.add();
crud("add");
}
public void delete() {
crudimpl.delete();
crud("delete");
}
public void update() {
crudimpl.update();
crud("update");
}
public void query() {
crudimpl.query();
crud("query");
}
public void crud (String msg){
System.out.println(msg+"方法开始执行");
}
}
4.测试类
package com.shxp.aop;
public class Crudtest {
public static void main(String[] args) {
Crudimpl crudimpl = new Crudimpl();
Crudservice crudservice = new Crudservice(crudimpl);
crudservice.add();
}
}
静态代理的利与弊
好处:
可以使得我们的真实角色更加纯粹 . 不再去关注一些公共的事情 .
公共的业务由代理来完成 . 实现了业务的分工 ,
公共业务发生扩展时变得更加集中和方便 .
缺点 :
类多了 , 多了代理类 , 工作量变大了 . 开发效率降低 .
我们想要静态代理的好处,又不想要静态代理的缺点,所以 , 就有了动态代理 !
8.动态代理实例(aop底层)
抽象角色租房类
package com.shxp.proxy;
public interface Rent {
/*抽象角色租房*/
public void rent();
}
真实对象
package com.shxp.proxy;
/*真实角色房东房东要出租房子*/
public class Host implements Rent{
public void rent() {
System.out.println("房东要出租房子");
}
}
代理角色
package com.shxp.proxy;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
/*代理角色*/
public class ProxyInvocationHandler implements InvocationHandler {
private Rent rent;
public void setRent(Rent rent) {
this.rent = rent;
}
/*生成代理类,重点是第二个参数,获取要代理的抽象角色!之前都是一个角色现在要代理一类角色*/
public Object getProxy(){
return Proxy.newProxyInstance(this.getClass().getClassLoader(),rent.getClass().getInterfaces(),this);
}
/* proxy :method 代理类的调用处理程序的方法对象*/
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
seeHouse();
Object result = method.invoke(rent,args);
fare();
return result;
}
//看房
public void seeHouse(){
System.out.println("带房客看房");
}
//收中介费
public void fare(){
System.out.println("收中介费");
}
}
客户端调用
package com.shxp.proxy;
public class Client {
public static void main(String[] args) {
/*真实对象*/
Host host = new Host();
/*代理实例的调用处理程序*/
ProxyInvocationHandler pih = new ProxyInvocationHandler();
pih.setRent(host);/*把真实对象放进去*/
Rent rent = (Rent)pih.getProxy();/*生成代理对象*/
rent.rent();
}
}
9.aop的三种实现方式
**1.使用spring的api接口(主要spring的api接口实现)**
需要织入的对象接口
package com.shxp.aoptest;
public interface UserService {
public void add();
public void delete();
public void update();
public void search();
}
对象接口的实现类
package com.shxp.aoptest;
public class UserServiceImpl implements UserService{
public void add() {
System.out.println("增加员工");
}
public void delete() {
System.out.println("删除员工");
}
public void update() {
System.out.println("修改员工");
}
public void search() {
System.out.println("查询员工");
}
}
需要切入对象的后置方法
package com.shxp.aoptest;
import org.springframework.aop.AfterReturningAdvice;
import java.lang.reflect.Method;
public class AfterLog implements AfterReturningAdvice {
//returnValue 返回值
//method被调用的方法
//args 被调用的方法的对象的参数
//target 被调用的目标对象
public void afterReturning(Object returnValue, Method method, Object[] args, Object target) throws Throwable {
System.out.println("执行了" + target.getClass().getName()
+"的"+method.getName()+"方法,"
+"返回值:"+returnValue);
}
}
需要切入对象的前置方法
package com.shxp.aoptest;
import org.springframework.aop.MethodBeforeAdvice;
import java.lang.reflect.Method;
public class Log implements MethodBeforeAdvice {
//method : 要执行的目标对象的方法
//objects : 被调用的方法的参数
//Object : 目标对象
public void before(Method method, Object[] objects, Object o) throws Throwable {
System.out.println( o.getClass().getName() + "的" + method.getName() + "方法被执行了");
}
}
spring配置
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:aop="http://www.springframework.org/schema/aop"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop.xsd">
<!--注册bean-->
<bean id="userService" class="com.shxp.aoptest.UserServiceImpl"/>
<bean id="log" class="com.shxp.aoptest.Log"/>
<bean id="afterLog" class="com.shxp.aoptest.AfterLog"/>
<!--aop的配置-->
<aop:config>
<!--切入点 expression:表达式匹配要执行的方法-->
<aop:pointcut id="pointcut" expression="execution(* com.shxp.aoptest.UserServiceImpl.*(..))"/>
<!--执行环绕; advice-ref执行方法 . pointcut-ref切入点-->
<aop:advisor advice-ref="log" pointcut-ref="pointcut"/>
<aop:advisor advice-ref="afterLog" pointcut-ref="pointcut"/>
</aop:config>
</beans>
**2.使用自定义类实现aop**
需要切入的类
package com.shxp.aoptest;
public class Advice {
public void before(){
System.out.println("=============方法执行前=============");
}
public void after(){
System.out.println("=============方法执行后=============");
}
}
spring配置
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:aop="http://www.springframework.org/schema/aop"
xsi:schemaLocation="http://www.springframework.org/schema/beans
https://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/aop
https://www.springframework.org/schema/aop/spring-aop.xsd
">
<bean id="userService" class="com.shxp.aoptest.UserServiceImpl"></bean>
<bean id="advice" class="com.shxp.aoptest.Advice"></bean>
<!--自定义类-->
<aop:config>
<!--自定义切面-->
<aop:aspect ref="advice">
<!--切入点-->
<aop:pointcut id="pointcut" expression="execution(* com.shxp.aoptest.UserServiceImpl.*(..)))"/>
<!--通知-->
<aop:before method="before" pointcut-ref="pointcut"></aop:before>
<aop:after method="after" pointcut-ref="pointcut"></aop:after>
</aop:aspect>
</aop:config>
</beans>
3.使用注解的方式实现aop
1.切面类
package com.shxp.aoptest;
import org.aspectj.lang.annotation.After;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.stereotype.Component;
@Component
@Aspect
public class Aspectj {
@After("execution(* com.shxp.aoptest.UserServiceImpl.*(..))")
public void after(){
System.out.println("======哈哈哈哈======");
};
}
1.需要开启aop注解,并且把类注册到spring中
<bean id="aspect" class="com.shxp.aoptest.Aspectj"></bean>
<aop:aspectj-autoproxy proxy-target-class="true"/>