spring的注解模式和AOP和自动装配

在Java中创建对象是通过构造方法进行创建的,如果构造方法设置为私有化防止其他人调用并(new)创建对象;

自动装配(Autowire)

其实就是为了让注入更加的简单实用了自动装配,
属性装配
类型装配

问题:为什么属性名称注入不直接通过属性名称注入,而通过反射找到set方法在找到属性注入;
解答(原因):因为属性注入只有两种注入:set方法注入和构造方法注入,所以要想属性注入就必须通过set / 构造方法进行注入;
这里的属性是注入后的实现类(接口)例如:private. UserDao. userDao。 这里 的userDao就是属性的名字


 private UserDao userDao;//基于Spring注入dao  面向接口编程 

 public void setUserDao(UserDao userDao) {
        this.userDao = userDao;
    }

在application.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 http://www.springframework.org/schema/beans/spring-beans.xsd">



   <!--user层-->
   <bean id="user" class="com.jt.pojo.User">
      <property name="id" value="100"></property>
     <!-- <property name="name" value="&lt;范冰冰&gt;"></property>-->
      <property name="name">
         <value><![CDATA[<范冰冰>]]></value>
      </property>
   </bean>
   
   <!--构建userdao-->
    <bean id="userDao" class="com.jt.dao.UserDaoImpl"></bean>

   <!--3.构建Service
      自动装配: 程序无需手动的编辑property属性
      autowire="byName" 根据属性的名称进行注入
         1.找到对象的所有的set方法 setUserDao()
         2.setUserDao~~~~set去掉~~~UserDao~~~~首字母小写~~~userDao属性
         3.Spring会根据对象的属性查询自己维护的Map集合,根据userDao名称,查找Map
         中的Key与之对应,如果匹配成功.则能自动调用set方法实现注入(必需有set方法)
      autowire="byType"  根据类型进行查找
         1.找到对象的所有的set方法 setUserDao()
         2.根据set方法找到该set方法中参数的类型UserDao.class
         3.Spring根据自己维护对象的Class进行匹配.如果匹配成功则实现注入(set方法)

      进行量使用bytype注入,使用byname容易包空指针错误
      自动装配!!!!!
      -->
   <bean id="userService" class="com.jt.service.com.jt.service.UserServiceImpl" autowire="byType"/>

   <!--4.构建Controller-->
   <bean id="userController" class="com.jt.controller.UserController" autowire="byName"/>

</beans>

controller的代码


package com.jt.controller;

import com.jt.pojo.User;
import com.jt.service.UserService;
import org.springframework.stereotype.Controller;


public class UserController {

    //spring容器负责注入Service对象
    private UserService userService;
    private User user;  //代替用户传入的数据

    public void setUser(User user) {
        this.user = user;
    }

    public void setUserService(UserService userService) {
        this.userService = userService;
    }

    public void addUser(){

       userService.addUser(user);
    }
}


service层的代码

package com.jt.service;

import com.jt.pojo.User;

public interface UserService {

    void addUser(User user);
}

service层的代码的实现类


package com.jt.service;

import com.jt.dao.UserDao;
import com.jt.pojo.User;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;


public class UserServiceImpl implements UserService{

    /**
     * 关于注解的说明
     * 1.@Autowired: 可以根据类型/属性名称进行注入 首先按照类型进行注入
     * 2.@Qualifier: 如果需要按照名称进行注入,则需要额外添加@Qualifier
     * 3.@Resource(type = "xxx.class",name="属性名称")
     * 关于注解补充: 由于@Resource注解 是由java原生提供的,不是Spring官方的.所以不建议使用
     */

    //@Autowired
    //@Qualifier(value = "属性的名称")
    //@Autowired
    private UserDao userDao;//基于Spring注入dao  面向接口编程

    public void setUserDao(UserDao userDao) {
        this.userDao = userDao;
    }

    @Override
    public void addUser(User user) {
        String name = user.getName() + "加工数据";
        user.setName(name);
        userDao.addUser(user);
    }
}


dao层的代码


package com.jt.dao;

import com.jt.pojo.User;

public interface UserDao {

    void addUser(User user);
}


dao层的代码实现类


package com.jt.dao;

import com.jt.pojo.User;
import org.springframework.stereotype.Controller;
import org.springframework.stereotype.Repository;
import org.springframework.stereotype.Service;

/**
 * <bean id="类名首字母小写~~userDaoImpl"  class="UserDaoImpl.class" />
 * 如果需要修改beanId则手动添加value属性即可
 */
@Repository(value = "userDao")
public class UserDaoImpl implements UserDao{

    @Override
    public void addUser(User user) {
        System.out.println("链接数据库执行insert into :"+user);
    }
}


pojo层的代码


package com.jt.pojo;

public class User { //通过容器为对象的属性赋值
    private Integer id;
    private String name;

    @Override
    public String toString() {
        return "User{" +
                "id=" + id +
                ", name='" + name + '\'' +
                '}';
    }

    public Integer getId() {
        return id;
    }

    public void setId(Integer id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }
}


注解模式

关于注解的说明

Spring为了简化xml配置方式,则研发注解模式.
Spring为了程序更加的严谨,通过不同的注解标识不同的层级 下面的这几种的注解作用是一样的,都是交给容器管理;


1).@Controller 用来标识Controller层的代码 相当于将对象交给Spring管理, 默认情况下是不生效的,要想生效需要在配置文件中使用包扫描

```java
<!--2.
      让注解生效,开启包扫描
      包路径特点: 给定包路径,则自动扫描同包及子孙包中的类
      base-package: 根据指定的包路径 查找注解
      写方式: 多个包路径 使用,号分隔
   -->
   <!--<context:component-scan base-package="com.jt.controller,com.jt.service,com.jt.dao"></context:component-scan>-->
   <context:component-scan base-package="com.jt"></context:component-scan>

2).@Service 用来标识Service层代码
3).@Repository 用来标识持久层
4).@Component 万用注解


 

**## 编辑配置文件**

```java

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:context="http://www.springframework.org/schema/context"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
                           http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">

   <!--1.构建user对象-->
   <bean id="user" class="com.jt.pojo.User">
      <property name="id" value="100"></property>
      <property name="name">
         <value><![CDATA[<范冰冰>]]></value>
      </property>
   </bean>

   
   
   <!--业务需求1: 只想扫描@controller注解
       属性说明: use-default-filters="true"
                默认规则 :true  表示可以扫描其他(所有)的注解
                        :false  按照用户指定的注解进行加载,默认规则不生效
   -->
   <context:component-scan base-package="com.jt" use-default-filters="false">
   <!--annotation:注解    expression:表达式指的是除了base-package=“”之外的包被扫描
      include:包含指的是那个注解可以被扫描,exclude:指的是那个注解不可以被扫描

->
      <context:include-filter type="annotation" expression="org.springframework.stereotype.Service"/>
   </context:component-scan>
	
	<!--业务需求2: 不想扫描@controller注解-->
   <context:component-scan base-package="com.jt">
      <!--通过包扫描 可以加载其他的注解 排除Controller注解。  exclude:指的是这个注解不可以被扫描->
      <context:exclude-filter type="annotation"
            expression="org.springframework.stereotype.Controller"/>
   </context:component-scan>
</beans>




注解使用原理

/**
 * <bean id="类名首字母小写~~userDaoImpl"  class="UserDaoImpl.class" />
 * 如果需要修改beanId则手动添加value属性即可
 */
@Repository(value = "userDao")
public class UserDaoImpl implements UserDao{

    @Override
    public void addUser(User user) {
        System.out.println("链接数据库执行insert into :"+user);
    }
}

使用全新的注解开发

 * 关于注解的说明
 * 1.@Autowired: 可以根据类型/属性名称进行注入 首先按照类型进行注入如果类型注入失败,则根据属性名称注入
 * 2.@Qualifier: 如果需要按照名称进行注入,则需要添加@Qualifier@Autowired
 *  * 3.@Resource(type = "xxx.class" 或 name="属性名称")
 * 关于注解补充: 由于@Resource注解 是由java原生提供的,不是Spring官方的.所以不建议使用
 上述的属性的注入在调用时 自动的封装了Set方法,所以Set方法可以省略不写


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值