2013-03-05 70 views
0

我将下面的代码添加到SQL Server查询中,现在必须在Oracle中执行相同的操作。我需要在视图中进行分组,而不是在C#中进行分组。我收到此错误消息:查询时出现Oracle错误

ORA-01747无效的user.table.column或列规范。

我该如何编写代码才能在Oracle中工作?

SELECT CTE.FACILITY_KEY, CTE.DATE, CTE.PATIENT_STATUS, COUNT(*) AS [COUNT] 
    FROM CTE 
    GROUP BY CTE.FACILITY_KEY, CTE.DATE, CTE.PATIENT_STATUS; 

在查询的开始,我有这个完整的代码在这里:

CREATE OR REPLACE VIEW DBD_V_CDL_CHANGES AS 
WITH CTE AS 
(
SELECT TR.FACILITY_KEY 
     , MV.VALUE_CODE 
     , CAST(COUNT(*) AS NUMERIC(9, 0)) COUNT 
    FROM OPTC.THS_T_TRANSACTIONS1 TR 
    JOIN OPTC.THS_M_MENU2 M 
     ON M.MENU_ID = TR.MENU_ID 
    JOIN OPTC.THS_M_VALUES MV 
     ON MV.MENU_ID = TR.MENU_ID_VALUE 
    JOIN OPTC.THS_M_VALUES MV2 
     ON MV2.MENU_ID = TR.PREVIOUS_MENU_ID_VALUE 
    JOIN OGEN.GEN_M_PATIENT_MAST PM 
     ON PM.PAT_NUMBER = TR.PAT_NUMBER 
    WHERE TR.TR_DATETIME BETWEEN TRUNC(SYSDATE) 
          AND TRUNC(SYSDATE) + 86399/86400 
    AND TR.EDIT_NO < 0 
    AND MV.VALUE_TYPE IS NULL 
    AND MV2.VALUE_TYPE IS NULL 
    AND MV.VALUE_CODE >= 0 
    AND MV2.VALUE_CODE >= 0 
    AND M.SUB_SYS_EXT = 'G1' 
    AND ABS(MV.VALUE_CODE - MV2.VALUE_CODE) > 1 
    AND (PM.DISCHARGE_DATE IS NULL OR PM.DISCHARGE_DATE < SYSDATE) 
    GROUP BY TR.FACILITY_KEY, MV.VALUE_CODE) 

    SELECT CTE.FACILITY_KEY, CTE.DATE, CTE.PATIENT_STATUS, COUNT(*) AS [COUNT] FROM CTE 
    GROUP BY CTE.FACILITY_KEY, CTE.DATE, CTE.PATIENT_STATUS; 
+0

视图定义是不完整的。你的意思是从视图中查询“DBC_V_CDL_CHANGES”吗? – Glenn 2013-03-05 20:45:55

+0

另请参阅[这里](http://www.techonthenet.com/oracle/errors/ora01747.php)了解ORA-01747的解释。它通常意味着你试图将保留字用作列。 – 2013-03-05 20:49:25

+0

CTE或COUNT非保留字。 – Booksman 2013-03-05 20:52:27

回答

2

我看到了一些东西你的代码错误。

首先,您选择以下三列FACILITY_KEYVALUE_CODE和计数在CTE

SELECT TR.FACILITY_KEY , 
    MV.VALUE_CODE , 
    COUNT(*) as Count -- note there is no need to CAST(COUNT(*) AS NUMERIC(9, 0)) this 
FROM OPTC.THS_T_TRANSACTIONS1 TR 

但是当你选择CTE你选择,你是不是在CTE返回列:

with cte as 
( 
    -- your query here does not return DATE or PATIENT_STATUS 
) 
SELECT CTE.FACILITY_KEY, 
    CTE.DATE, 
    CTE.PATIENT_STATUS, 
    COUNT(*) AS COUNT 
FROM CTE 
GROUP BY CTE.FACILITY_KEY, CTE.DATE, CTE.PATIENT_STATUS; 

何处来自PATIENT_STATUSDate,因为你在你的CTE不包括他们?所以当你试图选择它们时,这些并不存在。

我通过在列表中包含未在CTE查询中选择的列来复制错误。

第二个问题是CTE.DATE列。 DATE是一个保留字,地方是双引号CTE."DATE"

+0

他们来自主查询。您有这些列是结果:FACILITY_KEY,DATE,PATIENT_STATUS – Booksman 2013-03-05 21:08:22

+0

@Booksman您在'select ... from cte'中返回的列必须位于主查询中,并且它们不在您的列表中。您只在主查询中返回3列。 – Taryn 2013-03-05 21:10:44

+0

@Booksman查看我的编辑。 'DATE'列是保留字,需要用双引号。 – Taryn 2013-03-05 21:28:56

0

... AS [COUNT],... AS NUMERIC(9,0))不是Oracle语法,将永远不会工作。只需删除[]并使用NUMBER而不是NUMERIC。不需要CAST Count()。 Count()函数将始终返回数字,例如0-0或某个数字。

这是Oracle有效的语法:

SELECT deptno, count(*) total_count_by_dept -- no need to cast or AS -- 
    FROM scott.emp 
GROUP BY deptno 
/

尽量不要使用保留字作为COUNT的别名:

SELECT CTE.FACILITY_KEY, CTE.DATE, CTE.PATIENT_STATUS, COUNT(*) AS total_cnt -- 'AS' is for clarity only, not required 
    FROM CTE 
GROUP BY CTE.FACILITY_KEY, CTE.DATE, CTE.PATIENT_STATUS 
/
+0

作为数字的演员工作。我测试了它,它在Oracle 11g和本演示中工作 - http://sqlfiddle.com/#!4/b8498/3 – Taryn 2013-03-05 22:06:01