概括潜在的Hibernate性能问题
学习Hibernate时,经常会遇到Hibernate性能问题,这里将介绍Hibernate性能问题的解决方法。
在使用Hibernate进行分页的过程中,如果你收到如下警告,那么这里就是一个潜在的Hibernate性能问题点:
WARNING: firstResult/maxResults specified with collection fetch; applying in memory!
出现这个警告的直接后果是:无论你想要看第几页的数据,从Hibernate打印出的SQL来看它总是查询了所有满足条件的结果。这是为什么呢?来看看这句警告所在的代码,它位于org.hibernate.hql.ast.QueryTranslatorImpl中,部分摘录如下:
view plaincopy to clipboardprint? QueryNode query = ( QueryNode ) sqlAst; boolean hasLimit = queryParameters.getRowSelection() != null && queryParameters.getRowSelection().definesLimits(); boolean needsDistincting = ( query.getSelectClause().isDistinct() || hasLimit ) && containsCollectionFetches(); QueryParameters queryParametersToUse; if ( hasLimit && containsCollectionFetches() ) { log.warn( "firstResult/maxResults specified with collection fetch; applying in memory!" ) RowSelection selection = new RowSelection(); selection.setFetchSize( queryParameters.getRowSelection().getFetchSize() ); selection.setTimeout( queryParameters.getRowSelection().getTimeout() ); queryParametersqueryParametersToUse = queryParameters.createCopyUsing( selection ); } else { queryParametersqueryParametersToUse = queryParameters; } List results = queryLoader.list( session, queryParametersToUse ); QueryNode query = ( QueryNode ) sqlAst; boolean hasLimit = queryParameters.getRowSelection() != null && queryParameters.getRowSelection().definesLimits(); boolean needsDistincting = ( query.getSelectClause().isDistinct() || hasLimit ) && containsCollectionFetches(); QueryParameters queryParametersToUse; if ( hasLimit && containsCollectionFetches() ) { log.warn( "firstResult/maxResults specified with collection fetch; applying in memory!" ); RowSelection selection = new RowSelection(); selection.setFetchSize( queryParameters.getRowSelection().getFetchSize() ); selection.setTimeout( queryParameters.getRowSelection().getTimeout() ); queryParametersqueryParametersToUse = queryParameters.createCopyUsing( selection ); } else { queryParametersqueryParametersToUse = queryParameters; } List results = queryLoader.list( session, queryParametersToUse );