使用hibernate时的困境

时间:2011-05-12 20:14:32

标签: java hibernate spring

我正在为我当前的项目使用两个表(它肯定会增长)。

第一张表有很多列,即

id|name|surname|age|token         |currentpackage|difference
1 |me  | you   | 22|xc2e2144124sd |100           |0

第二张表:

id|mirror|token|        connsize|price
81|server|xc2e2144124sd|100mbps |1000

这些表格充满了数据。 table1中有一些行与table2中的行具有相同的标记值。

我已经google了很多解决方案,这是我发现的最好的:

http://www.mkyong.com/hibernate/hibernate-one-to-one-relationship-example/http://www.vaannila.com/hibernate/hibernate-example/hibernate-mapping-one-to-one-1.html

但我不认为这些适用于我的情况(或他们)。在这些示例中,关系是增量的关键,我的令牌就是它在数据库中的方式。

我的最终目标是能够计算当前包装和价格之间的差异

你会为此推荐什么?我正在使用java / hibernate / spring

有没有其他方法告诉hibernate通过别的其他主键链接? 一些自定义键如表1中的标记? token是表一和表二之间的某种关系。它的很多(table1)到一个(table2)。

最新更新

我正在尝试通过使用查询来减去这两列:

UPDATE packages tl 
SET difference = (select (t2.price-t1.currentpackage) 
from packages t1, mirrors t2 
where t2.token= t1.token)

我收到了这个错误:

ERROR:  more than one row returned by a subquery used as an expression

我必须尝试过很多选项,但没有选择

尝试了同样的结果:

UPDATE packages X 
SET difference = (select Y.price-X.currentpackage
FROM packages X
LEFT OUTER JOIN mirrors Y
ON Y.token = X.token)

这似乎是我正在寻找的,但我无法将其纳入我的查询中:

Subtract Values from Two Different Tables

2 个答案:

答案 0 :(得分:3)

如果没有在第二个表中使用token标识符,您将无法将此关系映射为多对一关系。也就是说,你可以做几件事:

  1. 你甚至需要关联表吗?如果您的最终目标是按照您的说法计算currentpackageprice之间的差异,那么您似乎可以在查询中执行此操作。
  2. 如果确实需要关联表,可以更改架构吗?我假设两个表中的id列都是主键。您可以将second_id列(使用任何适当的名称)添加到第一个表中,该表将成为第二个表的外键,并将它们映射为多对一表。
  3. 如果您无法添加新列,是否可以在第二个表中将token作为主键?它是唯一的/不是空的吗?实际上,这是最后的手段,因为它将涉及在数据库中生成id值和/或在Hibernate中映射自定义插入以保留现有的表结构。
  4. 修改(根据更新的问题):

    现在这与Hibernate没什么关系,因为你试图执行的查询是(a)更新和(b)基于SQL的,但是......假设我理解你并且你正在尝试更新第一个表以包含第二个表中的相应行与第一个表中的当前行之间的差异,您可以执行以下操作:

    update packages
       set difference = (select price
                          from mirrors m
                         where m.token = packages.token
       ) - currentpackage
    

    根据您的RDBMS,语法可能略有不同;并非所有这些都支持更新中的相关子查询。有些支持多表更新(如MySQL或Postgres),您可以将查询编写为:

    update packages, mirrors
       set difference = mirrors.price - currentpackage
     where packages.token = mirrors.token
    

答案 1 :(得分:1)

让Hibernate通过其中一个表的主键之外的其他东西来连接表是很棘手的。你有时可以通过Hibernate喜欢的方式进行连接并将你的“逻辑连接”条件放入are子句来解决这个问题。

如果没有Hibernate所希望的连接条件并为您的逻辑提供套件,那么您将不得不做笛卡尔积。