【问题标题】:Hibernate Criteria vs HQL: which is faster? [closed]Hibernate Criteria vs HQL:哪个更快? [关闭]
【发布时间】:2011-05-23 00:32:12
【问题描述】:

我一直在阅读一些答案,但我仍然感到困惑。为什么?因为您提到的差异与性能无关。它们与易于使用有关。(Objetc(标准)和 SQL(hql))。但我想知道“标准”是否由于某种原因比 hql 慢。

我在另一个答案中读到了这个

“HQL 和criteriaQuery 在性能方面存在差异,每次使用criteriaQuery 触发查询时,它都会为表名创建一个新别名,该别名不会反映在任何数据库的最后查询缓存中。这会导致编译生成的 SQL 的开销,需要更多时间来执行。”作者:瓦伦·梅塔。

这是非常接近但是!我在另一个网站上阅读(http://gary-rowe.com/agilestack/tag/hibernate/)Hibernate 3.3 及更高版本不再是这种情况(请阅读:9)Hibernate 很慢,因为由Criteria接口不一致)

我已经做了一些测试,试图找出差异,但两者都生成 qry,并且不会更改表的别名。

我很困惑。如果有人知道主要原因,请帮助我们。谢谢

【问题讨论】:

    标签: performance hibernate hql hibernate-criteria


    【解决方案1】:

    我是 2004 年编写 Hibernate 3 查询翻译器的人,所以我知道它是如何工作的。

    Criteria 理论上应该比 HQL 查询具有更少的开销(命名查询除外,我将介绍它)。这是因为 Criteria 不需要解析任何内容。 HQL 查询使用基于 ANTLR 的解析器进行解析,然后将生成的 AST 转换为 SQL。但是,使用 HQL/JPAQL,您可以定义命名查询,其中 SQL 是在 SessionFactory 启动。理论上,命名查询的开销比 Criteria 少。

    因此,就 SQL 生成开销而言,我们有:

    1. 命名的 HQL/JPAQL 查询 - SQL 生成只发生一次。
    2. 标准 - 生成前无需解析。
    3. (未命名)HQL/JPAQL 查询 - 解析,然后生成。

    也就是说,在我看来,根据解析和 SQL 生成的开销来选择查询技术可能是一个错误。与在具有真实数据的真实数据库服务器上执行真实查询相比,这种开销通常非常小。如果在分析应用程序时确实出现了这种开销,那么也许您应该切换到命名查询。

    在选择 Criteria 和 HQL/JPAQL 时,我会考虑以下几点:

    • 首先,您必须确定您的代码中是否OK依赖于 Hibernate 专有 API。 JPA 没有标准。
    • Criteria 非常擅长处理许多可选搜索参数,例如您可能会在具有多参数“搜索表单”的典型网页上找到这些参数。使用 HQL,开发人员倾向于使用 StringBuilder 来处理 where 子句表达式(避免这种情况!)。使用 Criteria,您无需这样做。 Hardik 发表了类似的观点。
    • HQL/JPAQL 可用于大多数其他事情,因为代码往往更小,更易于开发人员理解。
    • 如果您使用 HQL,则可以将真正频繁的查询转换为命名查询。在进行一些分析之后,我更愿意稍后再执行此操作。

    【讨论】:

    • JPA doesn't have Criteria ?
    • @destan 从 JPA 2.x 开始,确实如此。 IIRC,JPA 1.x 没有。
    • @JoshuaDavis 很好的解释。我只是想知道为什么我们必须避免使用 StringBuilder 来构造 HQL。例如,如何处理可选参数?
    • @bruno.zambiazi 如果您正在通过字符串连接构建 JPAQL/HQL,那么您很可能有一个动态查询,这就是 Criteria 查询功能的用途。我倾向于将 Criteria 用于任何动态的东西(例如,查询根据用户输入而变化很大)。 HTH - 乔什
    • @GokulRajK.N.从 Criteria 或 JPQL 生成 SQL 时,显式或隐式连接应该没有太大区别。通常,执行连接比生成 SQL 花费的时间要长得多,因此在两者之间切换在大多数情况下不会产生明显的差异。
    【解决方案2】:

    我正在处理数百万条记录。我发现 HQL 比 Criteria 快得多。标准在性能方面滞后很多。

    如果您要处理大量数据,请选择 HQL。

    【讨论】:

    • 这对我来说没有多大意义。如果你有一个非常大的数据集,那么大部分时间都花在等待数据库处理查询上。在这种情况下,从 HQL 或 Criteria 生成 SQL 所需的时间并不重要。唯一使用 JPAQL 命名查询 vs '直接' JPAQL vs Criteria 的情况是当您执行相同的查询多次次。数据集的大小根本不重要。
    • 可能是您没有以正确的方式使用 Criteria。或者您是否为数百万条记录中的每一条都创建了一个新的 Criteria Query 对象?
    • 可能生成的SQL的访问计划不同。这并不意味着 Criteria 的错。
    【解决方案3】:

    我认为 Criteria 优于 HQL 的其他优势

    编写 HQL 会使代码变得混乱。 它看起来不再像编写干净的面向对象代码了。

    在编写 Criteria Queries 时,IDE 建议我们使用 Intellisense,因此除非我们在双引号中写入变量名之类的内容,否则犯错的可能性较小。

    【讨论】:

    • 对于复杂的查询,HQL 比 Criteria 更易读。
    【解决方案4】:

    我最喜欢动态查询的条件查询。例如,根据某些参数动态添加一些排序或保留一些部分(例如限制)要容易得多。

    另一方面,我将 HQL 用于静态和复杂查询,因为它更容易理解/阅读 HQL。此外,我认为 HQL 更强大一些,例如适用于不同的连接类型。

    JPA and Hibernate - Criteria vs. JPQL or HQL

    【讨论】:

    • Criteria 可以做 HQL 可以做的大多数连接类型,尽管有时它有点尴尬或难以理解(至少在我看来)。 HQL 更易于阅读,这绝对是正确的!
    • 顺便说一句,我会为你的答案投票……但你并没有真正回答 kcobuntu 的问题。
    • 如果您要复制别人的答案,您至少应该提及它。原答案链接:stackoverflow.com/a/197496/980103
    • 嗯..我是一个新手,我们在 SO 上没有多少用户/版主。
    【解决方案5】:

    你是对的,不是的。 使用org.hibernate.loader.Loader 类从数据库或缓存中检索结果列表。未启用缓存时,使用在 SessionFactoryImp 中创建的 Dialect 对象构建准备好的语句。因此,每个列表调用都会初始化语句。 此外,低级查询是自动生成的。基本上,它是一种辅助,但在某些情况下,手动编写特定查询会更有效。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-10-08
      • 2020-02-12
      • 1970-01-01
      • 2020-12-28
      • 1970-01-01
      • 2012-07-11
      • 2012-12-24
      相关资源
      最近更新 更多