计算Oracle中的平均值

时间:2015-11-18 08:57:09

标签: oracle oracle11g oracle10g

我想计算Oracle表中的平均值

CREATE TABLE AGENT_HISTORY(
  EVENT_ID INTEGER NOT NULL,
  AGENTID INTEGER NOT NULL,
  EVENT_DATE DATE NOT NULL
)
/

CREATE TABLE CPU_HISTORY(
  CPU_HISTORY_ID INTEGER NOT NULL,
  EVENT_ID INTEGER NOT NULL,
  CPU_NAME VARCHAR2(50 ) NOT NULL,
  CPU_VALUE NUMBER NOT NULL
)
/

我使用这个SQL查询:

----- FOR 24 HOURS CPU
    CURSOR LAST_24_CPU_CURSOR IS
      --SELECT EVENT_DATE, CPU FROM AGENT_HISTORY WHERE NAME = NAMEIN AND EVENT_DATE >= SYSDATE-(60*24)/1440;

      SELECT START_DATE, NVL(AVG(CH.CPU_VALUE),0)
          FROM (SELECT START_DATE - (LVL+1)/24 START_DATE, START_DATE - LVL/24 END_DATE
          FROM (SELECT SYSDATE START_DATE, LEVEL LVL FROM DUAL CONNECT BY LEVEL <= 24))
     LEFT JOIN AGENT_HISTORY AH ON EVENT_DATE BETWEEN START_DATE AND END_DATE
     LEFT JOIN CPU_HISTORY CH ON AH.EVENT_ID = CH.EVENT_ID
     JOIN AGENT AG ON AH.AGENTID = AG.ID
         WHERE AG.NAME = NAMEIN
          GROUP BY START_DATE
     ORDER BY 1;

此查询仅打印一个平均值。我想修改它以打印每小时平均值24个值。你能帮我修改一下这个问题吗?

2 个答案:

答案 0 :(得分:1)

我猜你的输入只包含给定间隔之一的数据;由于您正在使用带有AGENT的INNER JOIN,而AGENT又过滤了AGENT_HISTORY,因此您可以有效地将所有LEFT JOIN转换为内部版本。

我建议你在AGENT和时间段之间使用CROSS JOIN代替:

with agent_history(event_date, agentid, event_id) as ( 
  select timestamp '2015-11-18 09:00:07', 1, 1001 from dual
),
agent(id, name) as (
  select 1, 'myAgent' from dual
),
cpu_history(event_id, cpu_value)  as (
  select 1001, 75.2 from dual
),
time_slots(start_date, end_date) as (
  SELECT START_DATE - (LVL + 1) / 24 START_DATE,
               START_DATE - LVL / 24 END_DATE
          FROM (SELECT SYSDATE START_DATE,
                       LEVEL   LVL
                  FROM DUAL
                CONNECT BY LEVEL <= 24)
)
SELECT START_DATE,
       NVL(AVG(CH.CPU_VALUE),
           0)
  FROM time_slots ts
  CROSS JOIN AGENT AG
  LEFT JOIN AGENT_HISTORY AH
    ON AH.AGENTID = AG.ID
   AND EVENT_DATE BETWEEN START_DATE AND END_DATE
  LEFT JOIN CPU_HISTORY CH
    ON AH.EVENT_ID = CH.EVENT_ID
 WHERE AG.NAME = 'myAgent'
 GROUP BY START_DATE
 ORDER BY 1;

这可确保您获得完整的24行(每个时间段一行)。

答案 1 :(得分:0)

start_dateto_char(start_date, 'hh24:mi')条款中将select更改为group by