2011-03-29 72 views
0

我想选择具有特定属性的实体。由于file属性会返回byte[],这会降低应用程序的速度,因此无法检索整个实体。但它会抛出ClassCastException选择具有特定属性的实体时发生ClassCastException

这里是实体:

@NamedQuery(name = "findAllGarbage", query = "SELECT g.filename, g.description, g.uploadDate FROM Garbage g;") 
@Entity 
public class Garbage { 

@Id 
@GeneratedValue 
@Column(nullable = false) 
private Long id; 
@Column(nullable = false) 
private String filename; 
@Column(nullable = false) 
private String fileType; 
@Column(nullable = false) 
private String uploadDate; 
@Column(nullable = false) 
private String destroyDate; 
@Lob 
@Column(nullable = false) 
private byte[] file; 
@Column(nullable = false) 
private String description; 
    //Getters and Setters... 

下面是数据访问EJB。方法findAllGarbage()是触发ClassCastException的方法。

@Stateless(name = "ejbs/SearchEJB") 
public class SearchEJB implements ISearchEJB { 


@PersistenceContext 
    private EntityManager em; 

    public List<Garbage> findAllGarbage() { 
     Query query = em.createNamedQuery("findAllGarbage"); 

     List<Garbage> gList = new ArrayList(); 

     for (Object o : query.getResultList()) { 

      Garbage tmpG = new Garbage(); 
      tmpG.setFilename(((Garbage) o).getFilename()); 
      tmpG.setUploadDate(((Garbage) o).getUploadDate()); 
      tmpG.setDescription(((Garbage) o).getDescription()); 

      gList.add(tmpG); 
     } 
     return gList; 
    } 
} 

回答

5

您得到ClassCastException的原因是您的getAllGarbage查询不返回垃圾实例的集合。查询被写入来专门返回与垃圾实例相关联的值的子集,而不是完整的垃圾对象。如果您调试该方法,您可能会注意到query.getResultsList()正在返回Object []的集合。 Object []应该与您的命名查询中指定的值相对应:文件名,描述和上传日期。

下面是应该工作的结果使用情况的示例。

for (Object o : query.getResultList()) { 
    Object[] cols = (Object[]) o; 
    Garbage tmpG = new Garbage(); 
    tmpG.setFilename(cols[0]); 
    tmpG.setDescription(cols[1]); 
    tmpG.setUploadDate(cols[2]); 

    gList.add(tmpG); 
} 

另一种方法是你的原生查询更改为

select g from Garbage g 

,这将导致在一个充满垃圾的实例返回,让您的原代码按预期执行。

在附注中,我建议您不要像对待示例代码那样对每个Garbage实例进行类转换。这种技术为应用程序增加了额外的开销,并使得代码难以长期维护。如果您要多次使用铸造对象,请创建一个变量来存储铸造的实例并重用它。

+0

至于替代(我也更喜欢btw),OP提到,这不是一个选项,请参阅相关的问题+答案:http://stackoverflow.com/questions/5460476/issue-rendering- jpql-custom-query-results-into-a-jsf-page – BalusC 2011-03-30 00:10:59

+0

for循环修复了类转换异常。谢谢。但sortBy函数不工作。 – sfrj 2011-03-30 08:30:31

1

如果您将文件信息延迟,那么它不会减慢应用程序。当你有一个包含大量数据的字段时,这是一种常见策略。

+0

我如何才能在我的实体中创建一个lazzy属性?那也是个好主意? – sfrj 2011-03-30 08:17:31

+0

@sfrj - 检查Lob注释的文档,它们显示了这种确切的情况(因为它对Lobs来说很常见):http://download.oracle.com/javaee/5/api/javax/persistence/Lob.html – jtahlborn 2011-03-30 16:30:19