如何将此本机SQL查询转换为HQL [英] How to transform this native SQL query to an HQL

查看:129
本文介绍了如何将此本机SQL查询转换为HQL的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

  string hql = 
@SELECT *
FROM
(SELECT a。*,rownum r__
FROM
(select f2.filmid,
f2.realisateurid,
f2.titre,
f2 .annesortie,
f2.langue,
f2.duree,
f2.resume,
f2.poster,
f2.qtytotal,
f2.qtydisponible从电影f2
其中f2.filmid(
)选择不同的f.filmid
从电影f,filmpays fp,pays p,filmgenre fg,genre g,informationpersonnel director,role r,informationpersonnel actor
其中f.filmid = fp.filmid
和fp.paysid = p.paysid
和f.filmid = fg.filmid
和fg.genreid = g.genreid
和f.realisateurid = director.personelid
和f.filmid = r.filmid
和r.personelid = actor.personelid
和f.qtydisponible> 0
和upper(f.titre)LIKE:titre
和f.annesortie> =:anneeLow AND f.annesortie< =:anneeHigh
和upper(g.Nomgenre)LIKE:风格
和upper(f.Langue)LIKE:langue
和上(p.Nom)LIKE:支付
和上(director.nom)LIKE:realisateur
和upper(actor.nom)LIKE:acteur)
order by f2.annesortie DESC, f2.titre)a
WHERE rownum< ((:page * 8)+1))
WHERE r__> =((((:page - 1)* 8)+1);
/ *开始交易* /
ITransaction tx = s.BeginTransaction();
IQuery query = s.CreateQuery(hql);
query.SetString(titre,%+ sp.Title.ToUpper()+% );
query.SetInt32(anneeLow,sp.YearLow);
query.SetInt32(anneeHigh,sp.YearHigh);
query.SetString(pays, + sp.Country.ToUpper()+%);
query.SetString(langue,%+ sp.Lang.ToUpper()+%);
查询。 SetString(genre,%+ sp.Genre.ToUpper()+%);
query.SetString(realisateur,%+ sp.Director.ToUpper()+% );
query.SetString(acteur,%+ sp.Actor.ToUpper()+%);
query.SetInt32(page,page);
IList< Film> movies = query.List< Film>();

tx.Commit();

返回电影;

我正在尝试g以100%hql的方式写入



类似于

 的IList<目录> moreCats = sess.CreateQuery(
from Cat as cat+
cat.Name ='Fritz'or cat.id =:id1 or cat.id =:id2
) .SetInt64(id1,id1)
.SetInt67(id2,id2)
.List< Cat>();

查阅hql文档后,我已经理解如何在hql中做一个简单的小查询,但是如果我从另一个select中选择一个complexe,就像我的查询一样,我应该如何继续?



谢谢

解决方案

HQL支持where语句中的子查询,所以子查询在哪里不应该引起麻烦。



你的from语句中的子查询并不需要我,你应该能够改变你的查询,让它不再拥有它。



删除查询的分页部分可能会有所帮助。这个分页应该通过在HQL查询对象上调用 .SetFirstResult(indexCalculatedFromYourPage) .SetMaxResults(yourPageSize)来完成。

当然,您需要映射实体上的所有必需列。大多数查询看起来已经与我兼容。

如果您也映射相关实体,您可以通过避免必须明确写入相关表的连接条件来简化where子查询。



注意:您的查询看起来像一个多标准搜索查询。与其写一个查询考虑所有参数(并且支持它们是空的/未指定的),通常更容易(并且通过这种方式更好地执行性能)动态地编写查询以忽略未提供的参数。为此,最好使用查询API,如查询的问题或 linq-to-nhibernate

编辑:我现在意识到你已经将问题标记为 nhibernate (.Net)和 hibernate (Java)。我已经链接的两个API是NHibernate。如果您使用的是Java,那么 hibernate的问题标准 api,也许还有一些我不知道的。

So I have this long complexe Native SQLQuery :

  string hql = 
    @"SELECT * 
    FROM 
   (SELECT a.*, rownum r__ 
   FROM  
   (select f2.filmid,
    f2.realisateurid, 
    f2.titre, 
    f2.annesortie, 
    f2.langue, 
    f2.duree, 
    f2.resume, 
    f2.poster, 
    f2.qtytotal, 
    f2.qtydisponible from film f2
   where f2.filmid in (
    select distinct f.filmid
       from film f, filmpays fp, pays p, filmgenre fg, genre g, informationpersonnel director, role r, informationpersonnel actor
       where f.filmid = fp.filmid
       and fp.paysid = p.paysid
       and f.filmid = fg.filmid
       and fg.genreid = g.genreid
       and f.realisateurid = director.personelid
       and f.filmid = r.filmid
       and r.personelid = actor.personelid
       and f.qtydisponible > 0
       and upper(f.titre) LIKE :titre
       and f.annesortie >= :anneeLow AND f.annesortie <= :anneeHigh
       and upper(g.Nomgenre) LIKE :genre
       and upper(f.Langue) LIKE :langue
       and upper(p.Nom) LIKE :pays
       and upper(director.nom) LIKE :realisateur
       and upper(actor.nom) LIKE :acteur)
       order by f2.annesortie DESC, f2.titre) a
        WHERE rownum < ((:page * 8) +1 ))
           WHERE r__ >= (((:page - 1) *8) +1) "; 
/*Begin transaction */
            ITransaction tx = s.BeginTransaction();
            IQuery query = s.CreateQuery(hql);
            query.SetString("titre", "%" + sp.Title.ToUpper() + "%");
            query.SetInt32("anneeLow", sp.YearLow);
            query.SetInt32("anneeHigh", sp.YearHigh);
            query.SetString("pays", "%" + sp.Country.ToUpper() + "%");
            query.SetString("langue", "%" + sp.Lang.ToUpper() + "%");
     query.SetString("genre", "%" + sp.Genre.ToUpper() + "%");
        query.SetString("realisateur", "%" + sp.Director.ToUpper() + "%");
        query.SetString("acteur", "%" + sp.Actor.ToUpper() + "%");
        query.SetInt32("page", page);
        IList<Film> movies = query.List<Film>();

        tx.Commit();

        return movies;

And I'm trying to write in a 100% hql way

something similar to

IList<Cat> moreCats = sess.CreateQuery(
    "from Cat as cat where " + 
    "cat.Name = 'Fritz' or cat.id = :id1 or cat.id = :id2"
).SetInt64("id1", id1)
.SetInt67("id2", id2)
.List<Cat>();

After consulting the hql documentation I have understand how to make a simple small query in hql , but what if I have a complexe select from another select , like my query , how should I proceed ?

Thank you

解决方案

HQL supports subqueries in where statement, so subquery in the where should not cause troubles.

The subqueries in your from statement does not look to me necessary, you should be able of changing your query for no more having it.

Removing the paging part of the query will probably help. This paging should be done by calling .SetFirstResult(indexCalculatedFromYourPage) and .SetMaxResults(yourPageSize) on the HQL query object.

Of course, you need to have mapped all the required columns on your entities. Most of your query looks already HQL compatible to me.
If you map related entities too, you may then simplify the where subquery by avoiding having to write explicitly the join condition of related tables.

Note: your query looks like a "multi-criteria" search query. Rather than writing one query taking into account all parameters (and supporting them being empty/unspecified), it is usually easier (and better for performances by the way) to write the query dynamically for ignoring parameters which were not supplied. And for this, better use a querying api like or .

Edit: I now realize you have tagged your question as both (.Net) and (Java). The two api I have linked are for NHibernate. If you are using Java, then there is the api, and maybe some other I do not know of.

这篇关于如何将此本机SQL查询转换为HQL的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆