Pregunta

Tengo una tabla con un campo de marca de tiempo de tipo fecha y hora. Necesito agregar los datos entre una hora de inicio y finalización definida en grupos x que representan intervalos de tiempo de igual longitud, donde x se proporciona como parámetro de función.

¿Cuál sería la mejor manera de hacer esto con Hibernate?

EDITAR: algunas explicaciones

Tabla mysql:

data_ts: datetime pk
value1 : int
value2 : bigint
...

Clase de entidad:

Calendar dataTs;
Integer value1;
BigDecimal value2;
...

Estoy buscando una consulta HQL que haga algo como

select max(c.value1), avg(c.value2) from MyClass c 
  where c.dataTs between :start and :end group by <interval>

donde todo el período de tiempo se agrupa en x intervalos de tiempo de igual tamaño.

Ejemplo:

Start : 2008-10-01 00:00:00   
End   : 2008-10-03 00:00:00 (2 days)
Groups: 32

necesitaría agruparse por un intervalo de tiempo de 1.5 horas (48 horas / 32):

2008-10-01 00:00:00 - 2008-10-01 01:29:59
2008-10-01 01:30:00 - 2008-10-01 02:59:59
2008-10-01 02:00:00 - 2008-10-01 04:29:59
...
¿Fue útil?

Solución

He intentado resolver el mismo problema. Tengo que agrupar los datos por un intervalo de 2 horas dentro de un día. De hecho, "puro" No se supone que Hibernate se use de esta manera. Entonces agregué la proyección SQL nativa a los criterios de Hibernate. Para su caso, podría verse así (estoy usando la sintaxis de MySQL y las funciones):

int hours = 2; // 2-hours interval

Criteria criteria = session.createCriteria( MyClass.class )
            .add( Restrictions.ge( "dataTs", start ) )
            .add( Restrictions.le( "dataTs", end ) );


ProjectionList projList = Projections.projectionList();
        projList.add( Projections.max( "value1" ) );
        projList.add( Projections.avg( "value2" ) );
        projList.add( Projections.sqlGroupProjection(
            String.format( "DATE_ADD( DATE( %s_.dataTs ), INTERVAL( HOUR( %s_.dataTs ) - HOUR( %s_.dataTs) %% %d ) HOUR) as hourly", criteria.getAlias(), criteria.getAlias(), criteria.getAlias(), hours ),
            String.format( "DATE_ADD( DATE( %s_.dataTs ), INTERVAL( HOUR( %s_.dataTs) - HOUR( %s_.dataTs ) %% %d ) HOUR)", criteria.getAlias(), criteria.getAlias(), criteria.getAlias(), hours ),
            new String[]{ "hourly" },
            new Type[]{ Hibernate.TIMESTAMP } )
        );
        criteria.setProjection( projList );

List results = criteria
            .setCacheable( false )
            .list();

El código se ve un poco feo pero resuelve el problema. Espero que la idea general sea útil para usted.

Otros consejos

Hibernate es para mapear entre un gráfico de objetos (entidades y tipos de valor) y su representación en una base de datos relacional.

De la descripción de su pregunta, realmente no menciona ninguna entidad que esté modelando, por lo que sugeriría que se despliegue en una consulta SQL nativa.

http://www.hibernate.org/hib_docs/reference /en/html/querysql.html

¿Quizás si publicó la estructura de la tabla, esto puede dar más contexto a su pregunta?

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top