萬盛學電腦網

 萬盛學電腦網 >> 腳本專題 >> javascript >> 解析JPA的視圖查詢問題

解析JPA的視圖查詢問題

        這篇文章主要是對JPA的視圖查詢問題進行了詳細的分析介紹,需要的朋友可以過來參考下,希望對大家有所幫助

昨天晚上遇到一個需求,每天早上要生成一份報告給各個部門的Leader。實現方式基本上確定為HTML格式的電子郵件。但是數據方面犯了難。原因在於數據庫中存儲的數據是跨表的,而且還要做count統計,這樣得到的結果就不是原生的MySQL表,我用的又是JPA技術。我們知道,使用JPA第一步就是映射實體,每一張表就至少對應一個實體(力求嚴謹,因為聯合主鍵時一張表會對應兩個對象)。可是對於靈活的查詢尤其是連接查詢,並不存在一個真正的表與其對應,怎麼樣才能解決呢?來,我們來舉個“栗子”          假設我們有兩張表,一張學院表,一張學生表。學院表裡存著學院ID和學院名稱,學生表裡存著學生的基本信息,包括學號、學院ID和學生姓名(其它較復雜的屬性我們不看了),正如下面的建表語句所示:     代碼如下: -- ---------------------------- -- Table structure for `depts` -- ---------------------------- DROP TABLE IF EXISTS `depts`; CREATE TABLE `depts` (   `deptId` int(11) unsigned NOT NULL AUTO_INCREMENT COMMENT '學院ID',   `deptName` varchar(50) NOT NULL COMMENT '學院名稱',   PRIMARY KEY (`deptId`) ) ENGINE=InnoDB AUTO_INCREMENT=14 DEFAULT CHARSET=utf8;   -- ---------------------------- -- Records of depts -- ---------------------------- INSERT INTO `depts` VALUES ('1', '哲學院'); INSERT INTO `depts` VALUES ('2', '經濟學院'); INSERT INTO `depts` VALUES ('3', '法學院'); INSERT INTO `depts` VALUES ('4', '教育學院'); INSERT INTO `depts` VALUES ('5', '文學院'); INSERT INTO `depts` VALUES ('6', '歷史學院'); INSERT INTO `depts` VALUES ('7', '理學院'); INSERT INTO `depts` VALUES ('8', '工學院'); INSERT INTO `depts` VALUES ('9', '農學院'); INSERT INTO `depts` VALUES ('10', '醫學院'); INSERT INTO `depts` VALUES ('11', '軍事學院'); INSERT INTO `depts` VALUES ('12', '管理學院'); INSERT INTO `depts` VALUES ('13', '藝術學院');     再建立一個學生表,再隨便往裡面插入點數據:  代碼如下: -- ---------------------------- -- Table structure for `students` -- ---------------------------- DROP TABLE IF EXISTS `students`; CREATE TABLE `students` (   `stuNo` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '學號 從1000開始',   `deptId` int(10) unsigned NOT NULL COMMENT '學院ID',   `stuName` varchar(50) NOT NULL COMMENT '學生姓名',   PRIMARY KEY (`stuNo`),   KEY `FK_DEPTID` (`deptId`),   CONSTRAINT `FK_DEPTID` FOREIGN KEY (`deptId`) REFERENCES `depts` (`deptId`) ON UPDATE CASCADE ) ENGINE=InnoDB AUTO_INCREMENT=1006 DEFAULT CHARSET=utf8;   -- ---------------------------- -- Records of students -- ---------------------------- INSERT INTO `students` VALUES ('1000', '13', '鳥叔'); INSERT INTO `students` VALUES ('1001', '7', '喬布斯'); INSERT INTO `students` VALUES ('1002', '3', '阿湯哥'); INSERT INTO `students` VALUES ('1003', '3', '施瓦辛格'); INSERT INTO `students` VALUES ('1004', '2', '貝克漢姆'); INSERT INTO `students` VALUES ('1005', '3', '讓雷諾');     現在我們想統計一下各個學院都有多少學生。這個題目在我們學習SQL的時候再簡單不過了。兩種實現方法:    使用Group By和不使用Group By:      代碼如下: SELECT b.deptId, b.deptName, count(*) as 'totalCount' FROM students a LEFT JOIN depts b ON a.deptId=b.deptId GROUP BY b.deptId ORDER BY b.deptId;   使用Group By之後,凡是沒有對應學生記錄的學院都沒有顯示出來(我不明白為什麼。。。如果有人知道的話麻煩告訴我好嗎?) 代碼如下: +--------+--------------+------------+ | deptId | deptName     | totalCount | +--------+--------------+------------+ |      2 | 經濟學院     |          1 | |      3 | 法學院       |          3 | |      7 | 理學院       |          1 | |     13 | 藝術學院     |          1 | +--------+--------------+------------+   再來一個不使用Group By的查詢: 代碼如下: SELECT a.deptId, a.deptName, (SELECT count(*) FROM students b where b.deptId=a.deptId) as 'totalCount' FROM depts a;   這次就完全顯示出來了:  復制代碼 代碼如下: +--------+--------------+------------+ | deptId | deptName     | totalCount | +--------+--------------+------------+ |      1 | 哲學院       |          0 | |      2 | 經濟學院     |          1 | |      3 | 法學院       |          3 | |      4 | 教育學院     |          0 | |      5 | 文學院       |          0 | |      6 | 歷史學院     |          0 | |      7 | 理學院       |          1 | |      8 | 工學院       |          0 | |      9 | 農學院       |          0 | |     10 | 醫學院       |          0 | |     11 | 軍事學院     |          0 | |     12 | 管理學院     |          0 | |     13 | 藝術學院     |          1 | +--------+--------------+------------+   至此,我們的SQL寫通了。但是怎麼才能使用JPA來查詢出一樣的視圖呢?    我們按照往常編碼那樣,從一個主要的實體操作服務中暴露出EntityManager來:   代碼如下: package net.csdn.blog.chaijunkun.dao;   import javax.persistence.EntityManager; import javax.persistence.PersistenceContext;   import org.springframework.stereotype.Service;   @Service public class ObjectDaoServiceImpl implements ObjectDaoService {    @PersistenceContext  private EntityManager entityManager;    @Override  public EntityManager getEntityManager(){   return this.entityManager;  }   }     這樣做的好處就是所有的數據操作都來源於同一個實體管理器。將來若部署發生變化,只改這一處注入就可以了。    然後我們還需要和以前一樣構造兩個表的實體類:   學院表的實體類:     代碼如下: package net.csdn.blog.chaijunkun.pojo;   import java.io.Serializable;   import javax.persistence.Column; import javax.persistence.Entity; import javax.persistence.GeneratedValue; import javax.persistence.GenerationType; import javax.persistence.Id; import javax.persistence.Table;   @Entity @Table(name="depts") public class Depts implements Serializable {    /**   *    */  private static final long serialVersionUID = 3602227759878736655L;    @Id  @GeneratedValue(strategy= GenerationType.AUTO)  @Column(name= "deptId")  private Integer deptId;    @Column(name= "deptName", length= 50, nullable= false)  private String deptName;    //getters and setters... }     學生表的實體類:  代碼如下: package net.csdn.blog.chaijunkun.pojo;   import java.io.Serializable;   import javax.persistence.Column; import javax.persistence.Entity; import javax.persistence.GeneratedValue; import javax.persistence.GenerationType; import javax.persistence.Id; import javax.persistence.JoinColumn; import javax.persistence.ManyToOne; import javax.persistence.Table;   @Entity @Table(name= "students") public class Students implements Serializable {    /**   *    */  private static final long serialVersionUID = -5942212163629824609L;    @Id
copyright © 萬盛學電腦網 all rights reserved