`
zhaoshg
  • 浏览: 258034 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

Ibatis动态查询例子(#和$以及iterate等的用法)

阅读更多

最近做了很多动态的查询,尤其是排序,以及一些状态字段,所以就做了一个总的动态查询,以不变应万变,呵呵

 

ibatis 里面的sql代码:

	<select id="getTopics" resultClass="topic" parameterClass="map">
			<![CDATA[
			        select * from p_Topic 
			]]>
		<dynamic prepend=" WHERE ">
			<isPropertyAvailable property="authorId">
				<isNotNull property="authorId" prepend=" and ">
					authorId=#authorId# 
                </isNotNull>
			</isPropertyAvailable>
			<isPropertyAvailable property="marketId">
				<isNotNull property="marketId" prepend=" and ">
					marketId=#marketId# 
                </isNotNull>
			</isPropertyAvailable>

			<isPropertyAvailable property="isDelete">
				<isNotNull property="isDelete" prepend=" and ">
					isDelete=#isDelete# 
                </isNotNull>
			</isPropertyAvailable>

			<isPropertyAvailable property="isBest">
				<isNotNull property="isBest" prepend=" and ">
					isBest=#isBest#
				</isNotNull>
			</isPropertyAvailable>

			<isPropertyAvailable property="statusStr">
				<isNotNull property="statusStr" prepend=" and ">
					$statusStr$
				</isNotNull>
			</isPropertyAvailable>
			<isPropertyAvailable property="marketIdList">
				<isNotNull property="marketIdList" prepend=" and marketId in ">
					<iterate property="marketIdList" conjunction="," close=")" open="(">
						#marketIdList[]#
					</iterate>
				</isNotNull>
			</isPropertyAvailable>
		</dynamic>

		<dynamic prepend=" order by ">
			<isPropertyAvailable property="orderStr">
				<isNotNull property="orderStr">
					$orderStr$
                </isNotNull>
			</isPropertyAvailable>
		</dynamic>

		<dynamic>
			<isPropertyAvailable property="begin">
				<isNotNull property="begin">
					limit #begin# 
                </isNotNull>
			</isPropertyAvailable>
			<isPropertyAvailable property="max" prepend=" , ">
				<isNotNull property="max">
					#max#
                </isNotNull>
			</isPropertyAvailable>
		</dynamic>
	</select>



	<select id="getTopicCount" resultClass="java.lang.Long"
		parameterClass="map">
			<![CDATA[
			        select count(id) from p_Topic 
			]]>
		<dynamic prepend=" WHERE ">
			<isPropertyAvailable property="authorId">
				<isNotNull property="authorId" prepend=" and ">
					authorId=#authorId# 
                </isNotNull>
			</isPropertyAvailable>
			<isPropertyAvailable property="marketId">
				<isNotNull property="marketId" prepend=" and ">
					marketId=#marketId# 
                </isNotNull>
			</isPropertyAvailable>

			<isPropertyAvailable property="isDelete">
				<isNotNull property="isDelete" prepend=" and ">
					isDelete=#isDelete# 
                </isNotNull>
			</isPropertyAvailable>

			<isPropertyAvailable property="isBest">
				<isNotNull property="isBest" prepend=" and ">
					isBest=#isBest#
				</isNotNull>
			</isPropertyAvailable>

			<isPropertyAvailable property="statusStr">
				<isNotNull property="statusStr" prepend=" and ">
					$statusStr$
				</isNotNull>
			</isPropertyAvailable>
			<isPropertyAvailable property="marketIdList">
				<isNotNull property="marketIdList" prepend=" and ">
					<iterate property="marketIdList" conjunction="," close=")" open=" marketId in (">
						#marketIdList[]#
					</iterate>
				</isNotNull>
			</isPropertyAvailable>
		</dynamic>
	</select>

这里需要注意的是:

①#xxx#  代表xxx是属性值,map里面的key或者是你的pojo对象里面的属性,ibatis会自动在它的外面加上引号,表现在sql语句是这样的 where xxx = 'xxx' ;

   而$xxxx$ 则是把xxxx作为字符串拼接到你的sql语句中,比如 order by  topicId , 如果你不用$来拼接而用#的话,外面就会被加上引号的哦    比如你的语句这样写  ... order by #xxx# (xxx就是你传进来的字符串topicId),ibatis 就会把他翻译成  order by 'topicId' 这样就报错了 ,用$的结果就是这样  order by topicId

②这里的iterate

<isPropertyAvailable property="marketIdList">
	<isNotNull property="marketIdList" prepend=" and marketId in ">
		<iterate property="marketIdList" conjunction="," close=")" open="(">
			#marketIdList[]#
		</iterate>
	</isNotNull>
</isPropertyAvailable>

 注意 iterate 的property属性 ,虽然你上面的isNotNull什么的都有这句,但这里一定要写清楚,否则ibatis会找不到你的list的

 

 

数据访问层代码:

public List<Topic> getTopics(Map<String, Object> map) {

		return getSqlMapClientTemplate().queryForList("getTopics", map);
	}

 服务层代码:

	public List<Topic> getTopicsByMarketIdList(Long authorId,List<Long> marketIdList,
			Integer orderby, Integer status, Pagination pagination) {
		Map<String, Object> map = new HashMap<String, Object>();
		map.put("authorId", authorId);
		map.put("isDelete", false);
		map.put("marketIdList", marketIdList);
		map.put("orderStr", "这里你组装你的order字符串");
		map.put("statusStr","这里你组装你的status字符串");
		map.put("begin", pagination.getOffset());
		map.put("max", pagination.getPageSize());
               //这个getTopicCount()方法和getTopics()大体是一致的,所以我的dao里面省略了它
		Long total = topicDao.getTopicCount(map);
		if (total == 0) {
			return new ArrayList<Topic>();
		} else {
			pagination.setTotal(total);
			List<Topic> res = topicDao.getTopics(map);
			return res;
		}
	}
 
public class Topic extends BaseObject implements Serializable {
	/**
	 * 
	 */
	private static final long serialVersionUID = -851973667810710701L;

	private Long id;
	private Long authorId;
	private String authorName;
	private Long marketId;
	private String title;
	private String tags;
	private String content;
	private Date pubdate;
	private Integer isBest;
	private Integer status;
	private Integer isDelete;
	private Integer clickCount;
	private Integer replyCount;
	private Date lastReplyTime;
       //getter and setter 省略...
}

Pagination代码:

public class Pagination {

	/**
	 * 要查看的页码
	 */
	private int page;

	/**
	 * 每页显示数
	 */
	private int pageSize;

	/**
	 * 一共有多少页
	 */
	private int totalPage;

	/**
	 * 一共有多少条记录
	 */
	private long total;

	/**
	 * 当前页的记录数
	 */
	private int size;

	/**
	 * 只需要topxx,不需要页数信息了
	 */
	private boolean topOnly;

      /**
       *从第几条记录开始	
       */
  	private int offset;
	
	public void setOffset(int offset) {
		this.offset = offset;
	}

	public Pagination(int page, int pageSize) {
		this.page = page;
		this.pageSize = pageSize;
	}

	public Pagination() {
	}

	public boolean require() {
		return pageSize > 0 ? true : false;
	}

	public int from() {
		return page * pageSize;
	}

	public int to() {
		return from() + size;
	}

	public int getPage() {
		return page;
	}

	public void setPage(int page) {
		this.page = page;
	}

	public int getPageSize() {
		return pageSize;
	}

	public void setPageSize(int pageSize) {
		this.pageSize = pageSize;
	}

	public int getTotalPage() {
		return totalPage;
	}

	public void setTotalPage(int totalPage) {
		this.totalPage = totalPage;
	}

	public long getTotal() {
		return total;
	}

	public void setTotal(long total) {
		this.total = total;
		if (pageSize > 0) {
			this.totalPage = (int) Math.ceil(total / (double) pageSize);
		} else {
			this.totalPage = 1;
		}
		if (page >= totalPage) {
			page = totalPage - 1;
		}
		if (page < 0)
			page = 0;
		if (pageSize > 0) {
			if (page < totalPage - 1)
				this.size = pageSize;
			else
				this.size = (int) (total % pageSize);
		} else {
			this.size = (int) total;
		}
		offset=page * pageSize;
	}

	public int getOffset() {
		return offset;
	}

	public int getSize() {
		return size;
	}

	public void setSize(int size) {
		this.size = size;
	}

	public boolean isTopOnly() {
		return topOnly;
	}

	public void setTopOnly(boolean topOnly) {
		this.topOnly = topOnly;
	}

}
分享到:
评论
3 楼 TonyLian 2009-11-05  
我觉得2楼提出的,只不过是看起来更漂亮而已,原写法也不会出现Bug
2 楼 zhaoshg 2009-08-11  
谢谢 lemonweirui 的更正,帮我发现了一个bug,谢谢
1 楼 lemonweirui 2009-08-04  
动态语句里的分句给予服用都还是提出来比较好。


        <isPropertyAvailable property="marketIdList">  
            <isNotNull property="marketIdList" prepend=" and marketId in ">  
                <iterate property="marketIdList" conjunction="," close=")" open="(">  
                    #marketIdList[]#  
                </iterate>  
            </isNotNull>  
        </isPropertyAvailable>

如果子句前的属性在参数对象中都不存在。
那么你动态生成的sql不符合逻辑了,改成下面的好些
         <isPropertyAvailable property="marketIdList">  
            <isNotNull property="marketIdList" prepend="and">  
                <iterate property="marketIdList" conjunction="," close=")" open=" marketId in (">  
                    #marketIdList[]#  
                </iterate>  
            </isNotNull>  
        </isPropertyAvailable>


相关推荐

    ibatis中输入输出各种类型的参数分析及#与$区别

    ### ibatis中输入输出各种类型的参数分析及#与$区别 #### iBatis简介与特点 ...通过对参数类型、`#`与`$`的区别以及`namespace`和`resultMap`的理解,可以帮助开发者更好地利用iBatis框架构建高效稳定的数据库访问层。

    ibatis中iterate的例子

    在iBatis中,`&lt;iterate&gt;`标签是一个非常实用的功能,它允许我们处理集合数据,如数组、List或Map等,进行循环遍历并生成动态SQL语句。下面我们将详细探讨`&lt;iterate&gt;`标签的用法及其示例。 `&lt;iterate&gt;`标签的主要...

    ibatis中 $ 于 # 的 区别

    它们各自有着独特的功能和应用场景,对于理解这两者的差异是十分重要的,因为这会直接影响到查询效率以及SQL注入等问题。 #### 1. # 前端符号的功能与特性 - **#{}** 表示预编译参数(PreparedStatement)。在...

    Ibatis资料ibatai sql map iBATIS使用$和#的一些理解

    在iBATIS中,有两种主要的方式来处理这些参数:使用`$`和`#`。这两种方式在不同的场景下有不同的效果。 首先,让我们来看看如何通过HashMap传递SQL参数。当SQL Map接口只能接受一个参数,但我们需要传递多个参数时...

    ibatis标签

    标题中的“ibatis&lt;iterate&gt;标签”指的是在iBATIS框架中用于动态SQL的一个关键功能。iBATIS是一个优秀的持久层框架,它允许将SQL语句直接嵌入到Java代码中,简化了数据库操作。而`&lt;iterate&gt;`标签是iBATIS提供的一个...

    ibatis资料

    在"Ibatis动态查询例子(#和$以及iterate等的用法) - Java - JavaEye论坛.mht"这个文件中,可能包含了JavaEye社区成员关于Ibatis动态查询的深入讨论和示例。这些讨论可能涵盖了实际开发中的问题和解决方案,比如如何...

    ibatis动态SQL标签用法

    iBatis动态SQL标签用法 iBatis是Java持久层框架,提供了动态SQL标签来实现动态查询。动态SQL标签可以根据不同的条件生成不同的SQL语句,从而提高查询效率和灵活性。 动态SQL片段 iBatis提供了动态SQL片段的功能,...

    操作数据库 iBATIS查询

    在iBATIS中,可以使用类似的方法来实现这样的查询。一种常见的错误写法是直接将`%`包含在SQL字符串中,如下所示: ```xml SELECT * FROM t_stu WHERE s_name LIKE #name# ``` 这种方式的问题在于,当调用查询时...

    ibatis的动态查询

    以上内容详细介绍了 ibatis 中动态查询的基本原理及具体实现方法,包括模糊查询、多条件组合查询以及使用 Map 作为参数的高级用法。这些知识点对于深入理解 ibatis 的动态查询机制非常重要,可以帮助开发者更高效地...

    Ibatis的简单例子(增删改查,联合查询等)

    在这个"Ibatis的简单例子"中,我们将探讨如何使用Ibatis进行数据库的增删改查(CRUD)操作以及联合查询。 1. **安装与配置**: 在开始之前,你需要在项目中添加Ibatis的依赖,通常是通过Maven或Gradle。在Maven的`...

    IBATIS动态查询语句.doc

    下面通过一个具体的例子来理解IBATIS动态查询的使用方法: ```xml select id, note from Product &lt;!-- isNotNull判断参数是否存在,Integer类型 --&gt; id=#id# &lt;!-- isNotEmpty判断字串不为空, isEmpty...

    ibatis_动态查询条件

    在动态查询条件中,iBatis 提供了多种判断参数的方法,例如 `isNotNull`、`isNotEmpty`、`isGreaterThan` 等,这些方法可以根据参数的值来生成不同的 SQL 语句。 下面是一个简单的示例,演示如何使用 iBatis 的动态...

    Ibatis复杂查询语句.doc

    总结起来,这个Ibatis查询语句充分展示了Ibatis处理复杂查询的能力,包括动态SQL、子查询、多表联接、条件判断、数据类型映射和迭代处理等功能。在实际开发中,这种灵活性使得Ibatis能够适应各种复杂的业务场景,...

    ibatis简单CRUD例子

    通过这些文件,新手可以学习如何配置Ibatis,以及如何在Java代码中使用Ibatis进行数据操作,从而理解Ibatis的工作原理和使用方法。 总结起来,Ibatis作为一个轻量级的持久层框架,其简单易用的特性使其成为许多项目...

    ibatis demo,ibatis例子,ibatis示例

    通过这个demo,你可以了解到Ibatis的基本用法,如何编写SQL映射文件,如何设计Mapper接口,以及如何在Java代码中调用这些接口执行数据库操作。同时,也能掌握Ibatis的动态SQL特性,以及如何配合Spring进行更高效的...

    使用的iBatis 简单例子

    在这个“使用的iBatis简单例子”中,我们将深入探讨如何配置和使用iBatis进行数据库交互。 首先,iBatis的核心组件包括XML配置文件、SQL映射文件以及SqlSessionFactory。XML配置文件用于定义数据源、事务管理器等...

    ibatis2.3例子代码

    通过学习这个例子,你可以了解到如何配置iBatis,如何编写SQL映射文件,以及如何在Java代码中使用SqlSession和Mapper接口来执行SQL语句。这对于理解和掌握iBatis框架以及数据库操作具有实际指导意义。

    Ibatis.net学习例子以及使用教程书

    通过本教程书的学习,你将掌握Ibatis.net的基本使用方法,包括查询、插入、更新和删除数据,以及如何处理复杂的业务场景。同时,你还将了解到如何结合其他.NET技术,如Entity Framework或NHibernate,以实现更高效、...

    .net中使用iBATIS的小例子

    下面我们将详细探讨iBATIS在.NET中的使用方法,以及如何利用提供的文件进行实践。 首先,了解iBATIS的基本概念。iBATIS是一个轻量级框架,它的核心功能是动态SQL映射,允许开发者编写SQL语句并将其封装到XML配置...

    ibatis sql语句对条件中特殊字符% # 处理

    通过对ibatis框架下SQL语句中特殊字符处理方法的详细分析,我们可以看到,合理地使用字符串转义处理结合动态SQL标签,可以有效地解决特殊字符带来的问题。这样不仅可以保证查询的准确性,还可以提高代码的健壮性和...

Global site tag (gtag.js) - Google Analytics