mybatis註解的使用

 

 

 

使用註解的話,就不需要在配置xml了,只需要寫接口就可以了,不過我建議使用註解來寫靜態sql語句,通過xml來寫動態sql,這樣更有效率。下面的有些屬性什麼意思,看過xml配置的基本都能從名字來轉換得知它的意思。遵循方式和xml的配置方式都是差不多的。

 

靜態sql情況下的使用

新增方式(@Insert)條件參數是數組,所以可以執行多條新增sql語句,格式就是@Insert(value= {" "," "," "...})

@Insert("insert into t_hus (hus_name,age,fk_wife_id) values (#{h.husbandName},#{h.age},#{h.wife.id})")
@Options(useGeneratedKeys=true,keyProperty="h.id")
void addHusbandBean(@Param("h") HusbandBean hus);

@Param("u")就是給參數取別名,在sql中去調用這個參數

 

刪除方式(@Delete)條件參數是數組,所以可以執行多條刪除sql語句,格式就是@Delete(value= {" "," "," "...})

@Delete({"delete from t_wife where id = #{h.wife.id};","delete from t_hus where id = #{h.id};"})
int deleteHusbandBean(@Param("h") HusbandBean hus);

 

修改方式(@Update)條件參數是數組,所以可以執行多條修改sql語句,格式就是@Update(value= {" "," "," "...})

@Update("update t_user set user_name=#{u.realName},login_name=#{u.userName},`password`=#{u.pwd},fk_role_id=#{u.userGradeValue},update_time=#{u.updateTime} where id=#{u.id}")
int updateUser(@Param("u")UserBean userBean);

 

查詢方式(@Select)條件參數是數組,所以可以執行多條查詢sql語句,格式就是@Select(value= {" "," "," "...})

1、@ResultType接收數據(就和xml中的resultType一樣),遵循規則與xml一樣(sql查詢出來的列的列別名必須和對象屬性一樣,保持一致。可以使用Map、基本數據類型、引用數據類型接收數據;如果是Map,取別名就以別名爲鍵,不取別名默認以列名作爲鍵名;如果是其他數據類型,比如本數據類型這些,那麼查詢的返回結果必須也是與之對應的單一結果,也就是一個結果)

@Select("select id,game_name as gameName from t_game")
@ResultType(GameBean.class)
List<GameBean> findAllGameBean();

@Param("u")就是給參數取別名,在@Select中我們才能方便去使用這個參數,使用方法就是: 別名.屬性

#{ }的作用就是取值的意思,傳入對象就用#{別名.屬性名};像對象這種層層結構的,比如Map就有這種結構,就可以這樣去取值;如果沒有這種結構,比如字符串這種單一類型,直接用#{別名} 

#{ }和${ }的作用都是取值,區別就是#{ }要進行預編譯,而${ }直接編譯
 

2、@Results接收數據(就是xml中的resultMap一樣,屬性這些就不具體說了)

@Select("select id,player_name from t_player where player_name like concat(#{p.playerName},'%')")
@Results({
 @Result(id=true,property="id",column="id",javaType=Integer.class),
 @Result(property="playerName",column="player_name",javaType=String.class)
 @Result(property="games",javaType=List.class,column="id",many=@Many(fetchType=FetchType.LAZY,select="getGameBeanById")) 
})
List<PlayerBean> findPlayerBeanListByObject(@Param("p") PlayerBean player);

 

動態sql的使用(自定義sql語句)

用來自定義的sql語句的四個註解:@SelectProvider、@InsertProvider、@UpdateProvider、@DeleteProvider;他們就是用來頂替@Select、@Insert、@Update、@Delete的;用了這幾個註解,我們就可以使用我們動態拼接的sql語句了。

這四個註解都有兩個屬性,type指定用的是哪個類,method指定用該類的哪個方法來實現動態sql返回

1、接口定義

@InsertProvider(type=UserSQLProvider.class,method="addBatchUserBean")
int addBatchUserBean(@Param("users") List<UserBean> users);

1、新建類和拼接sql的方法(不管方法中的邏輯怎麼寫,你只需要返回的是一個sql語句就行了)

public class UserSQLProvider {

	/**
	 * 無法規避SQL注入的問題
	 * 
	 * 返回必須是String,因爲要返回sql語句;
	 * 用Map<String,Object> params可以獲取接口方法的參數,通過鍵值去獲取參數值,就是接口中@Param() 取的別名去獲取
	 * @param params 固定參數
	 * @return 固定返回
	 * @throws ParseException
	 */
	public String addBatchUserBean(Map<String,Object> params) throws ParseException {
		
		StringBuilder sb = new StringBuilder("insert into t_user(login_name,user_name,user_pwd,age,gender,birthday,create_time) values ");
		List<UserBean> users = (List<UserBean>) params.get("users");
		
		
		//這串代碼  使用的是直接編譯
		for (UserBean user : users) {
			sb.append("('"+user.getLoginName()+"','"+user.getUserName()+"','"+user.getPassword()+"','"+user.getAge()+"','"+user.getGender()+"','"+DateUtil.date2Str(user.getBirthday(), "yyyy-MM-dd")+"',now()),");
		}
		
		String sql = sb.toString().substring(0, sb.toString().length() - 1);
		System.out.println(sql);
		
		return sql;
	}

}

接口方法使用了@Param註解的話,那麼相應sql拼裝方法必須接受Map<String, Object>做爲參數,通過鍵值去獲取參數值,就是接口中@Param() 取的別名去獲取。

對於只有一個參數的情況,可以直接使用,將參數直接傳入sql拼接的方法。比如:

@SelectProvider(type = SqlProvider.class, method = "selectUser")
@ResultMap("userMap")
public User getUser(long userId);
public class SqlProvider {
      public String selectUser(long userId) {
            return "select * from user where userId=" + userId;
     }
}

@ResultMap是我們去調取xml中的方法,所以如果都用註解了,這樣調取豈不是多此一舉,用@Results就行了,上面有說明。

接口中如果沒有參數傳入的話,就sql方法也可以不寫參數。

 

 

級聯關係:

一對一的情況(one=@One):對於丈夫來說,它有一個妻子

@Select("select id,hus_name,age,fk_wife_id from t_hus where id = #{id}")
@Results({
 @Result(id=true,property="id",column="id",javaType=Integer.class),
 @Result(property="husbandName",column="hus_name",javaType=String.class),
 @Result(property="age",column="age",javaType=Integer.class),
 @Result(property="wife",javaType=WifeBean.class,column="fk_wife_id",one=@One(fetchType=FetchType.LAZY,select="com.gezhi.mybatis01.o2omag.mapper.WifeMapper.getWifeBeanById"))
})
HusbandBean getHusbandBeanById(@Param("id")int id);

一對多的情況(many=@Many):對一個老師來說,他對應多個學生

@Select("select id,teacher_name,age from t_teacher where id = #{id}")
@Results({
 @Result(id=true,property="id",column="id",javaType=Integer.class),
 @Result(property="teacherName",column="teacher_name",javaType=String.class),
 @Result(property="age",column="age",javaType=Integer.class),
 @Result(property="stus",javaType=List.class,column="id",many=@Many(fetchType=FetchType.LAZY,select="findStudentBeanByFkTeacherId"))
})
TeacherBean getTeacherBeanById(@Param("id") int id);
	

@Select("select id,student_name as studentName,age from t_student where fk_teacher_id = #{id}")
@ResultType(StudentBean.class)
StudentBean findStudentBeanByFkTeacherId(@Param("id") int id);

多對多的情況(需要中間表來關聯多對多的兩張表,依然用many=@Many,通過中間表來查詢另一張表的信息)

@Select("select g.id,g.game_name as gameName from t_game as g,t_player_game as pg where g.id = pg.fk_game_id and fk_player_id = #{id}")
@ResultType(GameBean.class)
GameBean getGameBeanById(@Param("id") int id);
	
	/**
	 * 根據玩家名稱查詢
	 * @param playerName
	 * @return
	 */
	
@Select("select id,player_name from t_player where player_name like concat(#{p.playerName},'%')")
 @Results({
 @Result(id=true,property="id",column="id",javaType=Integer.class),
 @Result(property="playerName",column="player_name",javaType=String.class),
 @Result(property="games",javaType=List.class,column="id",many=@Many(fetchType=FetchType.LAZY,select="getGameBeanById"))
})
List<PlayerBean> findPlayerBeanListByObject(@Param("p") PlayerBean player);

鑑別器的情況(其餘的不說了,概念什麼的,只能說一下父類是寵物pet類,子類是狗類DogBean,還有貓類CatBean)

@Select("select id,pet_name,pet_type,bone,fish from t_pet")
@Results({ 
	@Result(id = true, property = "id", column = "id", javaType = Integer.class),
	@Result(property = "petName", column = "pet_name", javaType = String.class) 
})
	//鑑別器的配置
@TypeDiscriminator(column = "pet_type", javaType = Integer.class, cases = {
		@Case(value = "0", type = DogBean.class, results = {
			@Result(property="bone",column="bone",javaType=Integer.class)
		}), 
		@Case(value = "1", type = CatBean.class, results = {
			@Result(property="fish",column="fish",javaType=Integer.class)
		})
})
List<PetBean> findAllPetBean();

 

通過即時加載的方式也調取對象中另一對象的屬性:(學生對象中含有一個老師對象)通過這種方式也可完成映射,但是就沒有了延時加載的效果。

@Select("select s.id,s.student_name,s.age, t.id as tId,t.teacher_name,t.age as tAge from t_student as s,t_teacher as t where s.fk_teacher_id = t.id")
@Results({
 @Result(id=true,property="id", column="id",javaType=Integer.class),
 @Result(property="studentName",column="student_name",javaType=String.class),
 @Result(property="age",column="age",javaType=Integer.class),
 @Result(property="teacher.id",column="tId",javaType=Integer.class),
 @Result(property="teacher.teacherName",column="teacher_name",javaType=String.class),
 @Result(property="teacher.age",column="tAge",javaType=Integer.class)
})
List<StudentBean> findAllStudentBeanAndTeacherBean();

 

動態sql:https://www.cnblogs.com/jhj117/p/5388748.html

註解的使用:https://blog.csdn.net/wfq784967698/article/details/78786001

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章