有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

javajpa查询。getResultList()以通用方式使用

我正在创建一个包含多个表的复杂查询,需要列出结果。通常,我使用EntityManager并将结果映射到JPA表示:

UserEntity user = em.find(UserEntity.class, "5");

然后我可以访问用户UserEntity类定义的所有值。但是如何访问从本机多表查询返回的字段值呢?我得到的是一张物品清单。到目前为止还可以,但那个物体是什么?大堆地图收藏

//simpleExample
Query query = em.createNativeQuery("SELECT u.name,s.something FROM user u, someTable s WHERE s.user_id = u.id");
List list = query.getResultList();

//do sth. with the list, for example access "something" for every result row.

我想答案很简单,但大多数例子只是展示了直接向targetClass强制转换时的用法

PS:在这个例子中,我当然可以使用类映射。但是在我的例子中someTable不是由JPA管理的,因此我没有实体,也没有它的类表示,因为我要加入20个表,所以我不想创建所有的类只是为了访问值


共 (6) 个答案

  1. # 1 楼答案

    由于可以使用JPA 2.0 TypedQuery

    TypedQuery<SimpleEntity> q = 
            em.createQuery("select t from SimpleEntity t", SimpleEntity.class);
    
    List<SimpleEntity> listOfSimpleEntities = q.getResultList();
    for (SimpleEntity entity : listOfSimpleEntities) {
        // do something useful with entity;
    }
    
  2. # 2 楼答案

    我也遇到了同样的问题,我找到了一个简单的解决方案:

    List<Object[]> results = query.getResultList();
    for (Object[] result: results) {
        SomeClass something = (SomeClass)result[1];
        something.doSomething;
    }
    

    我知道这并不是最优雅的解决方案,也不是最佳实践,但至少对我来说是有效的

  3. # 3 楼答案

    如果您需要一种更方便的方法来访问结果,那么可以将任意复杂的SQL查询的结果转换为Java类,只需最少的麻烦:

    Query query = em.createNativeQuery("select 42 as age, 'Bob' as name from dual", 
            MyTest.class);
    MyTest myTest = (MyTest) query.getResultList().get(0);
    assertEquals("Bob", myTest.name);
    

    该类需要声明为@Entity,这意味着您必须确保它具有唯一的@Id

    @Entity
    class MyTest {
        @Id String name;
        int age;
    }
    
  4. # 4 楼答案

    这是对我有用的例子。我认为实体类中需要put方法来将sql列映射到java类属性

        //simpleExample
        Query query = em.createNativeQuery(
    "SELECT u.name,s.something FROM user u,  someTable s WHERE s.user_id = u.id", 
    NameSomething.class);
        List list = (List<NameSomething.class>) query.getResultList();
    

    实体类:

        @Entity
        public class NameSomething {
    
            @Id
            private String name;
    
            private String something;
    
            // getters/setters
    
    
    
            /**
             * Generic put method to map JPA native Query to this object.
             *
             * @param column
             * @param value
             */
            public void put(Object column, Object value) {
                if (((String) column).equals("name")) {
                    setName(String) value);
                } else if (((String) column).equals("something")) {
                    setSomething((String) value);
                }
            }
        }
    
  5. # 5 楼答案

    上面的查询返回对象[]的列表。因此,如果您想从列表中获取u.name和s.something,那么您需要迭代并为相应的类转换该值

  6. # 6 楼答案

    一般规则如下:

    • 如果select包含单个表达式,并且它是一个实体,那么结果就是那个实体
    • 如果select包含单个表达式,并且它是一个基元,那么结果就是该基元
    • 如果select包含多个表达式,则结果是Object[]包含相应的原语/实体

    所以,在你的例子中listList<Object[]>