1. 程式人生 > >Hibernate Criteria查詢之多表連線分頁-1

Hibernate Criteria查詢之多表連線分頁-1

最近嘗試用Hibernate的Criteria查詢實現多表連線下的分頁,發現一些Hibernate的奇怪問題:多表連線後的分頁求總條數始終報錯,檢查生成的sql也不正確。研究許久找到問題所在,特貼如下:

Mysql指令碼如下:

學生 測試資料,請勿見笑:)

/*
Navicat MySQL Data Transfer

Source Server         : localhost
Source Server Version : 50018
Source Host           : localhost:3306
Source Database       : house

Target Server Type    : MYSQL
Target Server Version : 50018
File Encoding         : 65001

Date: 2011-08-10 13:38:12
*/

SET FOREIGN_KEY_CHECKS=0;
-- ----------------------------
-- Table structure for `district`
-- ----------------------------
DROP TABLE IF EXISTS `district`;
CREATE TABLE `district` (
  `ID` int(11) NOT NULL auto_increment,
  `name` varchar(50) NOT NULL,
  PRIMARY KEY  (`ID`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

-- ----------------------------
-- Records of district
-- ----------------------------
INSERT INTO `district` VALUES ('1', '青羊區');
INSERT INTO `district` VALUES ('2', '金牛區');
INSERT INTO `district` VALUES ('3', '撫琴小區');
INSERT INTO `district` VALUES ('4', '朝陽區');
INSERT INTO `district` VALUES ('5', '陽光小區');
INSERT INTO `district` VALUES ('6', '名揚小區');

-- ----------------------------
-- Table structure for `house`
-- ----------------------------
DROP TABLE IF EXISTS `house`;
CREATE TABLE `house` (
  `ID` int(11) NOT NULL auto_increment,
  `user_id` int(11) NOT NULL,
  `type_id` int(11) NOT NULL,
  `title` varchar(50) NOT NULL,
  `description` varchar(2000) NOT NULL,
  `price` int(11) NOT NULL,
  `pubdate` date NOT NULL,
  `floorage` int(11) NOT NULL,
  `contact` varchar(255) NOT NULL,
  `street_id` int(11) NOT NULL,
  PRIMARY KEY  (`ID`),
  KEY `fk_user_house` (`user_id`),
  KEY `fk_type_house` (`type_id`),
  KEY `fk_street_house` (`street_id`),
  CONSTRAINT `fk_street_house` FOREIGN KEY (`street_id`) REFERENCES `street` (`ID`),
  CONSTRAINT `fk_type_house` FOREIGN KEY (`type_id`) REFERENCES `type` (`ID`),
  CONSTRAINT `fk_user_house` FOREIGN KEY (`user_id`) REFERENCES `users` (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

-- ----------------------------
-- Records of house
-- ----------------------------
INSERT INTO `house` VALUES ('1', '1', '1', '第一個房子', '很好,向陽,方便舒適', '1234', '2011-07-26', '123', '1354135423', '1');
INSERT INTO `house` VALUES ('2', '2', '2', '第二個房子', '簡單傢俱,寬敞明亮', '4543', '2011-07-04', '343', '1435465656', '3');
INSERT INTO `house` VALUES ('3', '1', '1', '第三個房子', '乾淨寬敞明亮', '123', '2011-07-13', '123', '1342533333', '3');
INSERT INTO `house` VALUES ('4', '3', '4', '第四個房子', '和低速復甦阿發塑封股', '214', '2011-07-04', '3444', '323243423442', '5');
INSERT INTO `house` VALUES ('5', '3', '3', '第五間房', '是不是哦馬哈好似奧揮灑出', '12', '2011-07-03', '878', '13541234567', '3');
INSERT INTO `house` VALUES ('6', '4', '2', '第六間房', '非hiusa公司udgfbsdugf 歲噶', '344', '2011-07-12', '546', '1423343243', '3');
INSERT INTO `house` VALUES ('8', '1', '4', 'wrwegrhtrhgh', 'dgv hyhhhhhhhhhhhhh', '44', '2011-07-11', '676', '154354545455', '1');
INSERT INTO `house` VALUES ('9', '1', '2', 'gfdgggggggggggggg', 'afdgdsgdgdf', '2342', '2011-06-27', '12423', '1535436546', '1');
INSERT INTO `house` VALUES ('10', '1', '2', 'dfegggg', 'fdfdgfd', '21423', '2011-07-10', '1243', '243254354', '1');
INSERT INTO `house` VALUES ('11', '2', '2', 'rrrrr', 'vdfgrdtg', '2423', '2011-07-11', '232', '13423432435', '2');

-- ----------------------------
-- Table structure for `street`
-- ----------------------------
DROP TABLE IF EXISTS `street`;
CREATE TABLE `street` (
  `ID` int(11) NOT NULL auto_increment,
  `name` varchar(50) NOT NULL,
  `district_id` int(11) NOT NULL,
  PRIMARY KEY  (`ID`),
  KEY `fk_street_district_id` (`district_id`),
  CONSTRAINT `fk_street_district_id` FOREIGN KEY (`district_id`) REFERENCES `district` (`ID`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

-- ----------------------------
-- Records of street
-- ----------------------------
INSERT INTO `street` VALUES ('1', '東南路', '1');
INSERT INTO `street` VALUES ('2', '知春路', '1');
INSERT INTO `street` VALUES ('3', '中關村大街', '2');
INSERT INTO `street` VALUES ('4', '學院路', '3');
INSERT INTO `street` VALUES ('5', '朝陽路', '3');
INSERT INTO `street` VALUES ('6', '成蔭路', '4');
INSERT INTO `street` VALUES ('7', '哈哈路', '3');

-- ----------------------------
-- Table structure for `type`
-- ----------------------------
DROP TABLE IF EXISTS `type`;
CREATE TABLE `type` (
  `ID` int(11) NOT NULL auto_increment,
  `name` varchar(10) NOT NULL,
  PRIMARY KEY  (`ID`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

-- ----------------------------
-- Records of type
-- ----------------------------
INSERT INTO `type` VALUES ('1', '一室一廳');
INSERT INTO `type` VALUES ('2', '兩室一廳');
INSERT INTO `type` VALUES ('3', '三室一廳');
INSERT INTO `type` VALUES ('4', '四室一廳');
INSERT INTO `type` VALUES ('5', '兩室兩廳');

-- ----------------------------
-- Table structure for `users`
-- ----------------------------
DROP TABLE IF EXISTS `users`;
CREATE TABLE `users` (
  `id` int(11) NOT NULL auto_increment,
  `name` varchar(50) NOT NULL,
  `password` varchar(50) NOT NULL,
  `telephone` varchar(15) NOT NULL,
  `userName` varchar(50) NOT NULL,
  `idAdmin` varchar(5) NOT NULL,
  PRIMARY KEY  (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

-- ----------------------------
-- Records of users
-- ----------------------------
INSERT INTO `users` VALUES ('1', 'admin', '12345', '13541305274', 'Admin', '1');
INSERT INTO `users` VALUES ('2', 'zhang', '12345', '12345678444', '張小花', '2');
INSERT INTO `users` VALUES ('3', 'li', '12345', '12234242354', 'zhngxaida', '1');
INSERT INTO `users` VALUES ('4', 'luo', 'luo', '143435y4385', 'hsafgdsavds', '1');
INSERT INTO `users` VALUES ('5', 'huang', 'huang', '14235435465', 'hdusigfsu', '1');

現有實體類如下:

區實體類:

package org.accp.mhouse.entities;

import java.util.HashSet;
import java.util.Set;
import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import static javax.persistence.GenerationType.IDENTITY;
import javax.persistence.Id;
import javax.persistence.OneToMany;
import javax.persistence.Table;

/**
 * District entity. @author MyEclipse Persistence Tools
 */
@Entity
@Table(name = "district", catalog = "house")
public class District implements java.io.Serializable {

	// Fields

	private Integer id;
	private String name;
	private Set<Street> streets = new HashSet<Street>(0);

	// Constructors

	/** default constructor */
	public District() {
	}

	/** minimal constructor */
	public District(String name) {
		this.name = name;
	}

	/** full constructor */
	public District(String name, Set<Street> streets) {
		this.name = name;
		this.streets = streets;
	}

	// Property accessors
	@Id
	@GeneratedValue(strategy = IDENTITY)
	@Column(name = "ID", unique = true, nullable = false)
	public Integer getId() {
		return this.id;
	}

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

	@Column(name = "name", nullable = false, length = 50)
	public String getName() {
		return this.name;
	}

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

	@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY, mappedBy = "district")
	public Set<Street> getStreets() {
		return this.streets;
	}

	public void setStreets(Set<Street> streets) {
		this.streets = streets;
	}

}

街道實體類:

package org.accp.mhouse.entities;

import java.util.HashSet;
import java.util.Set;
import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import static javax.persistence.GenerationType.IDENTITY;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.OneToMany;
import javax.persistence.Table;

/**
 * Street entity. @author MyEclipse Persistence Tools
 */
@Entity
@Table(name = "street", catalog = "house")
public class Street implements java.io.Serializable {

	// Fields

	private Integer id;
	private District district;
	private String name;
	private Set<House> houses = new HashSet<House>(0);

	// Constructors

	/** default constructor */
	public Street() {
	}

	/** minimal constructor */
	public Street(District district, String name) {
		this.district = district;
		this.name = name;
	}

	/** full constructor */
	public Street(District district, String name, Set<House> houses) {
		this.district = district;
		this.name = name;
		this.houses = houses;
	}

	// Property accessors
	@Id
	@GeneratedValue(strategy = IDENTITY)
	@Column(name = "ID", unique = true, nullable = false)
	public Integer getId() {
		return this.id;
	}

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

	@ManyToOne(fetch = FetchType.LAZY)
	@JoinColumn(name = "district_id", nullable = false)
	public District getDistrict() {
		return this.district;
	}

	public void setDistrict(District district) {
		this.district = district;
	}

	@Column(name = "name", nullable = false, length = 50)
	public String getName() {
		return this.name;
	}

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

	@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY, mappedBy = "street")
	public Set<House> getHouses() {
		return this.houses;
	}

	public void setHouses(Set<House> houses) {
		this.houses = houses;
	}

}


房屋型別實體類:

package org.accp.mhouse.entities;

import java.util.HashSet;
import java.util.Set;
import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import static javax.persistence.GenerationType.IDENTITY;
import javax.persistence.Id;
import javax.persistence.OneToMany;
import javax.persistence.Table;

/**
 * Type entity. @author MyEclipse Persistence Tools
 */
@Entity
@Table(name = "type", catalog = "house")
public class Type implements java.io.Serializable {

	// Fields

	private Integer id;
	private String name;
	private Set<House> houses = new HashSet<House>(0);

	// Constructors

	/** default constructor */
	public Type() {
	}

	/** minimal constructor */
	public Type(String name) {
		this.name = name;
	}

	/** full constructor */
	public Type(String name, Set<House> houses) {
		this.name = name;
		this.houses = houses;
	}

	// Property accessors
	@Id
	@GeneratedValue(strategy = IDENTITY)
	@Column(name = "ID", unique = true, nullable = false)
	public Integer getId() {
		return this.id;
	}

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

	@Column(name = "name", nullable = false, length = 10)
	public String getName() {
		return this.name;
	}

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

	@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY, mappedBy = "type")
	public Set<House> getHouses() {
		return this.houses;
	}

	public void setHouses(Set<House> houses) {
		this.houses = houses;
	}

}


使用者實體類:

package org.accp.mhouse.entities;

import java.util.HashSet;
import java.util.Set;
import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import static javax.persistence.GenerationType.IDENTITY;
import javax.persistence.Id;
import javax.persistence.OneToMany;
import javax.persistence.Table;

/**
 * Users entity. @author MyEclipse Persistence Tools
 */
@Entity
@Table(name = "users", catalog = "house")
public class Users implements java.io.Serializable {

	// Fields

	private Integer id;
	private String name;
	private String password;
	private String telephone;
	private String userName;
	private String idAdmin;
	private Set<House> houses = new HashSet<House>(0);

	// Constructors

	/** default constructor */
	public Users() {
	}

	/** minimal constructor */
	public Users(String name, String password, String telephone,
			String userName, String idAdmin) {
		this.name = name;
		this.password = password;
		this.telephone = telephone;
		this.userName = userName;
		this.idAdmin = idAdmin;
	}

	/** full constructor */
	public Users(String name, String password, String telephone,
			String userName, String idAdmin, Set<House> houses) {
		this.name = name;
		this.password = password;
		this.telephone = telephone;
		this.userName = userName;
		this.idAdmin = idAdmin;
		this.houses = houses;
	}

	// Property accessors
	@Id
	@GeneratedValue(strategy = IDENTITY)
	@Column(name = "id", unique = true, nullable = false)
	public Integer getId() {
		return this.id;
	}

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

	@Column(name = "name", nullable = false, length = 50)
	public String getName() {
		return this.name;
	}

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

	@Column(name = "password", nullable = false, length = 50)
	public String getPassword() {
		return this.password;
	}

	public void setPassword(String password) {
		this.password = password;
	}

	@Column(name = "telephone", nullable = false, length = 15)
	public String getTelephone() {
		return this.telephone;
	}

	public void setTelephone(String telephone) {
		this.telephone = telephone;
	}

	@Column(name = "userName", nullable = false, length = 50)
	public String getUserName() {
		return this.userName;
	}

	public void setUserName(String userName) {
		this.userName = userName;
	}

	@Column(name = "idAdmin", nullable = false, length = 5)
	public String getIdAdmin() {
		return this.idAdmin;
	}

	public void setIdAdmin(String idAdmin) {
		this.idAdmin = idAdmin;
	}

	@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY, mappedBy = "users")
	public Set<House> getHouses() {
		return this.houses;
	}

	public void setHouses(Set<House> houses) {
		this.houses = houses;
	}

}


房屋實體類:

package org.accp.mhouse.entities;

import java.util.Date;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import static javax.persistence.GenerationType.IDENTITY;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.Table;
import javax.persistence.Temporal;
import javax.persistence.TemporalType;

/**
 * House entity. @author MyEclipse Persistence Tools
 */
@Entity
@Table(name = "house", catalog = "house")
public class House implements java.io.Serializable {

	// Fields

	private Integer id;
	private Users users;//many to one
	private Type type;//many to one
	private Street street;//many to one
	private String title;
	private String description;
	private Integer price;
	private Date pubdate;
	private Integer floorage;
	private String contact;

	// Constructors

	/** default constructor */
	public House() {
	}

	/** full constructor */
	public House(Users users, Type type, Street street, String title,
			String description, Integer price, Date pubdate, Integer floorage,
			String contact) {
		this.users = users;
		this.type = type;
		this.street = street;
		this.title = title;
		this.description = description;
		this.price = price;
		this.pubdate = pubdate;
		this.floorage = floorage;
		this.contact = contact;
	}

	// Property accessors
	@Id
	@GeneratedValue(strategy = IDENTITY)
	@Column(name = "ID", unique = true, nullable = false)
	public Integer getId() {
		return this.id;
	}

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

	@ManyToOne(fetch = FetchType.LAZY)
	@JoinColumn(name = "user_id", nullable = false)
	public Users getUsers() {
		return this.users;
	}

	public void setUsers(Users users) {
		this.users = users;
	}

	@ManyToOne(fetch = FetchType.LAZY)
	@JoinColumn(name = "type_id", nullable = false)
	public Type getType() {
		return this.type;
	}

	public void setType(Type type) {
		this.type = type;
	}

	@ManyToOne(fetch = FetchType.LAZY)
	@JoinColumn(name = "street_id", nullable = false)
	public Street getStreet() {
		return this.street;
	}

	public void setStreet(Street street) {
		this.street = street;
	}

	@Column(name = "title", nullable = false, length = 50)
	public String getTitle() {
		return this.title;
	}

	public void setTitle(String title) {
		this.title = title;
	}

	@Column(name = "description", nullable = false, length = 2000)
	public String getDescription() {
		return this.description;
	}

	public void setDescription(String description) {
		this.description = description;
	}

	@Column(name = "price", nullable = false)
	public Integer getPrice() {
		return this.price;
	}

	public void setPrice(Integer price) {
		this.price = price;
	}

	@Temporal(TemporalType.DATE)
	@Column(name = "pubdate", nullable = false, length = 10)
	public Date getPubdate() {
		return this.pubdate;
	}

	public void setPubdate(Date pubdate) {
		this.pubdate = pubdate;
	}

	@Column(name = "floorage", nullable = false)
	public Integer getFloorage() {
		return this.floorage;
	}

	public void setFloorage(Integer floorage) {
		this.floorage = floorage;
	}

	@Column(name = "contact", nullable = false)
	public String getContact() {
		return this.contact;
	}

	public void setContact(String contact) {
		this.contact = contact;
	}

}


查詢示範1,查詢區為“xxx”區的所有房屋資訊,並抓取查詢房屋物件關聯的街道物件,街道物件關聯的區物件

首先查詢總條數,通常思維習慣如下:

//求總條數
			session
				.createCriteria(House.class)
				.setFetchMode("street", org.hibernate.FetchMode.JOIN)
				.setFetchMode("street.district",org.hibernate.FetchMode.JOIN)
				.createAlias("street.district", "d")
				.add(Restrictions.eq("d.name", "青羊區"))
				.setProjection(Projections.rowCount())
				.uniqueResult();

很遺憾,查詢結果大失所望:

控制異常如下:

Hibernate: 
    select
        count(*) as y0_ 
    from
        house.house this_ 
    where
        d1_.name=?
Exception in thread "main" org.hibernate.exception.SQLGrammarException: could not execute query
	at org.hibernate.exception.SQLStateConverter.convert(SQLStateConverter.java:67)
	at org.hibernate.exception.JDBCExceptionHelper.convert(JDBCExceptionHelper.java:43)
	at org.hibernate.loader.Loader.doList(Loader.java:2220)
	at org.hibernate.loader.Loader.listIgnoreQueryCache(Loader.java:2108)
	at org.hibernate.loader.Loader.list(Loader.java:2103)
	at org.hibernate.loader.criteria.CriteriaLoader.list(CriteriaLoader.java:94)
	at org.hibernate.impl.SessionImpl.list(SessionImpl.java:1570)
	at org.hibernate.impl.CriteriaImpl.list(CriteriaImpl.java:283)
	at org.hibernate.impl.CriteriaImpl.uniqueResult(CriteriaImpl.java:305)
	at org.accp.mhouse.dao.MainModule.main(MainModule.java:164)
Caused by: com.mysql.jdbc.exceptions.jdbc4.MySQLSyntaxErrorException: Unknown column 'd1_.name' in 'where clause'
	at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
	at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:39)
	at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:27)
	at java.lang.reflect.Constructor.newInstance(Constructor.java:513)
	at com.mysql.jdbc.Util.handleNewInstance(Util.java:406)
	at com.mysql.jdbc.Util.getInstance(Util.java:381)
	at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:1030)
	at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:956)
	at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3491)
	at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3423)
	at com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:1936)
	at com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:2060)
	at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2542)
	at com.mysql.jdbc.PreparedStatement.executeInternal(PreparedStatement.java:1734)
	at com.mysql.jdbc.PreparedStatement.executeQuery(PreparedStatement.java:1885)
	at org.hibernate.jdbc.AbstractBatcher.getResultSet(AbstractBatcher.java:187)
	at org.hibernate.loader.Loader.getResultSet(Loader.java:1791)
	at org.hibernate.loader.Loader.doQuery(Loader.java:674)
	at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:236)
	at org.hibernate.loader.Loader.doList(Loader.java:2217)
	... 7 more


但是以上語句如果是查詢結果那是絕對正確的,如下:

//結果
			session
				.createCriteria(House.class)
				.setFetchMode("street", org.hibernate.FetchMode.JOIN)
				.setFetchMode("street.district",org.hibernate.FetchMode.JOIN)
				.createAlias("street.district", "d")
				.add(Restrictions.eq("d.name", "青羊區"))
				.list();


控制檯輸出如下:

Hibernate: 
    select
        this_.ID as ID2_2_,
        this_.contact as contact2_2_,
        this_.description as descript3_2_2_,
        this_.floorage as floorage2_2_,
        this_.price as price2_2_,
        this_.pubdate as pubdate2_2_,
        this_.street_id as street8_2_2_,
        this_.title as title2_2_,
        this_.type_id as type9_2_2_,
        this_.user_id as user10_2_2_,
        street3_.ID as ID1_0_,
        street3_.district_id as district3_1_0_,
        street3_.name as name1_0_,
        d1_.ID as ID4_1_,
        d1_.name as name4_1_ 
    from
        house.house this_ 
    inner join
        house.street street3_ 
            on this_.street_id=street3_.ID 
    inner join
        house.district d1_ 
            on street3_.district_id=d1_.ID 
    where
        d1_.name=?


就是上面那個求總條數的問題困擾我許久,網路搜尋無果,幾經查詢摸索,正確如下:

求總條數:

//求總條數
			session
				.createCriteria(House.class)
				.createAlias("street","st",CriteriaSpecification.INNER_JOIN)
				.createAlias("st.district","d",CriteriaSpecification.INNER_JOIN)
				.createAlias("users", "u", CriteriaSpecification.INNER_JOIN)
				.createAlias("type","t",CriteriaSpecification.INNER_JOIN)
				.add(Restrictions.eq("d.name", "青羊區"))
				.setProjection(Projections.rowCount())
				.uniqueResult();

Hibernate API文件對createAlias()方法的解釋:

createAlias

Parameters:
associationPath - A dot-seperated property path
alias - The alias to assign to the joined association (for later reference).
joinType - The type of join to use.
Returns:
this (for method chaining)
Throws:

很明顯上面的查詢更加複雜,房屋關聯街道,街道關聯區,房屋關聯型別,房屋關聯使用者,篩選條件是區是“青羊區”,我們看查詢結果:

Hibernate: 
    select
        count(*) as y0_ 
    from
        house.house this_ 
    inner join
        house.street st1_ 
            on this_.street_id=st1_.ID 
    inner join
        house.district d2_ 
            on st1_.district_id=d2_.ID 
    inner join
        house.type t4_ 
            on this_.type_id=t4_.ID 
    inner join
        house.users u3_ 
            on this_.user_id=u3_.id 
    where
        d2_.name=?


OK,終於搞定這個棘手的問題。