SQL : Sommer des Timestamps

Prenons directement un exemple :
Vous avez une table Oracle nommée TASKS_EXECUTIONS contenant un ensemble de tâches exécutées avec une date de début (BEGIN) et une date de fin (END) d’exécution dans des champs de type TIMESTAMP.

Voici cette table :

TASK

BEGIN END

1

01/01/12 00:00:00,000000000

01/01/12 02:40:00,000000000

2

02/01/12 00:00:00,000000000

03/01/12 03:20:45,120000000

3 03/01/12 00:00:00,000000000

04/01/12 01:30:20,455000000

Vous souhaitez obtenir la somme des durées de ces tâches sous forme de chaîne de caractères au format Dd HH24:MI:SS :

TOTAL_TASKS_DURATION

2d 07:31:05

La requête suivante (que l’on pourrait avoir tendance à faire instinctivement)…

select sum(exec.END-exec.BEGIN) TOTAL_TASKS_DURATION
from TASKS_EXECUTIONS;

…provoque l’erreur : « ORA-00932: types de données incohérents ; attendu : NUMBER ; obtenu : TIMESTAMP« .
Malheureusement, nous sommes donc contraints en quelque sorte de « parser » les champs de type TIMESTAMP pour en extraire les composantes, avant de recalculer le total et le rendre présentable :

select floor(ts_sum/60/60/24)||'d'
   ||TO_CHAR(TO_DATE(MOD(trunc(ts_sum),60*60*24),'SSSSS')
,'HH24:MI:SS') TOTAL_TASKS_DURATION
from (
   select sum(extract(second from END-BEGIN)
      +extract(minute from END-BEGIN)*60
      +extract(hour from END-BEGIN)*60*60
      +extract(day from END-BEGIN)*60*60*24) ts_sum
   from TASKS_EXECUTIONS
);