Skip to content
Home » Oracle » 如何解決ORA-00904 無效的 ID

如何解決ORA-00904 無效的 ID

ORA-00904 Invalid Identifier - Oracle Database Object Name Recognition Examples

ORA-00904

ORA-00904表示您在語句中使用了不匹配的欄位名或不正確的語法。通常,錯誤不僅發生在SELECTINSERT中,還發生在UPDATEDELETECREATE TABLEALTER TABLE和PL/SQL塊中。

大多數使用者不會相信錯誤,但事實上SQL解析器從未犯過任何錯誤。在這篇文章中,您可能會看到一些關於ORA-00904的錯誤模式,其中一個可能與您的情況相符。由於大多數使用者錯誤是由區分大小寫的問題引起的,因此我們必須首先解釋鬆散形式精確形式之間的差異。

通常,Oracle會將大多數識別字排除在密碼之外,並將其視為不區分大小寫的識別字。但是在ORA-00904無效識別字的情況下應該注意一些特殊用法。

不僅ORA-00904,ORA-00903和ORA-00911也與物件識別碼的無效使用有關。更具體地說,ORA-00903警告用戶無效的表名,並引發ORA-00911來定位非法字元

鬆散形式與精確形式

根據Oracle資料庫物件名稱和限定詞,有兩種有效的命名形式來創建資料庫物件。一個是非引用識別字,另一個是帶引號的識別字。為了避免ORA-00904,您必須知道兩種命名形式之間的明顯差異。

非引用識別字(鬆散形式)

它們沒有標點符號或任何其他特殊處理。只要它們基本上是等效的字串,我們就可以在SQL語句中不區分大小地靈活使用它們。所以我通常在這篇文章中將其稱為鬆散形式。實際上,非引用識別字都被認為是上層識別字。這個概念將幫助您更好地瞭解ORA-00904。

帶引號的識別字(精確形式)

它們以雙引號("")開頭和結尾。您可以將幾乎所有字元放在雙引號中,包括空格和保留字。這種識別字應該與最初定義的完全一致。所以我通常在這篇文章中將其稱為精確形式。據我所知,這是ORA-00904的主要來源。

稍後,我們還將討論有關ORA-00904的更多問題,以區分引用的和未引用的識別字。

ORA-00904的錯誤模式

在大多數情況下,濫用欄位名是ORA-00904的主要來源,其餘的是語法錯誤。在這篇文章中,我們將在以下部分討論ORA-00904的幾種錯誤模式。

  1. SELECT或INSERT中的ORA-00904
  2. WHERE,ORDER BY或GROUP BY中的ORA-00904
  3. CREATE TABLE中的ORA-00904
  4. ALTER TABLE中的ORA-00904
  5. PL/SQL中的ORA-00904
  6. Toad Error ORA-00904: "REF": invalid identifier

A. SELECT或INSERT中的ORA-00904

SELECTINSERT中列出的任何欄位都有機會生成此錯誤。

在本節中,ORA-00904會警告用戶出現問題,這可能是由以下原因之一引起的:

  1. 不存在的欄位
  2. 不存在的功能
  3. 拼寫錯誤的欄位
  4. 區分大小寫的欄位
  5. 欄位名稱中的空白

1. 由於不存在的欄位而導致的ORA-00904

通常,我們創建一個表而不使用雙引號:

SQL> create table all_names_1 (First_Name varchar2(25), Last_Name varchar2(25));

Table created.

然後我們插入一些資料。

SQL> insert into all_names_1 select distinct first_name, last_name from employees;

107 rows created.

要避免使用ORA-00904,您應該在沒有任何引號的情況下查詢此表。也就是說,低位或大寫的欄位名都是有效且可接受的。這是因為SQL解析器會將所有識別字視為大寫識別字。

SQL> select first_name, last_name from all_names_1 where first_name = 'Scott';

FIRST_NAME                LAST_NAME
------------------------- -------------------------
Scott                     Rowe

使用這種通常創建的表格可以保證它不再具有ORA-00904了嗎?讓我們看看兩種常見類型的無效識別字。

第一種情況是選擇表中不存在的欄位。

SQL> select first_name, last_name, num from all_names_1 where first_name = 'Scott';
select first_name, last_name, num from all_names_1 where first_name = 'Scott'
                              *
ERROR at line 1:
ORA-00904: "NUM": invalid identifier
SQL> insert into all_names_1 (first_name, last_name, num) values ('Scott', 'Rowe', 100);
insert into all_names_1 (first_name, last_name, num) values ('Scott', 'Rowe', 100)
                                                *
ERROR at line 1:
ORA-00904: "NUM": invalid identifier
ORA-00904 Toad for Oracle中的無效識別字
ORA-00904 Toad for Oracle中的無效識別字

我們知道,欄位NUM是無效欄位,因為它不存在於表中。我們最好通過描述表來檢查定義。

SQL> desc all_names_1;
 Name                                      Null?    Type
 ----------------------------------------- -------- ----------------------------
 FIRST_NAME                                         VARCHAR2(25)
 LAST_NAME                                          VARCHAR2(25)

如果您對表中缺少該欄位感到驚訝,則有可能已被其他人刪除。

2. 由於不存在的函數而導致的ORA-00904

這種模式很少見,我們應該討論不存在的函式呼叫。讓我們看看我們如何複製ORA-00904。

SQL> select first_name, month(hire_date) hire_month from employees where last_name = 'Rowe';
select first_name, month(hire_date) hire_month from employees where last_name = 'Rowe'
                   *
ERROR at line 1:
ORA-00904: "MONTH": invalid identifier

SQL解析器首先嘗試匹配名為MONTH的函數,但沒有找到任何內容,因此它轉向匹配欄位,也沒有匹配,SQL解析器別無選擇,只能拋出ORA-00904。這讓我想起MySQL確實有MONTH功能,但Oracle沒有。不存在功能的原因相同:ORA-00904:"DATEDIFF":識別字無效

ORA-00904的解決方案是使用正確Oracle的函數名為EXTRACT來獲取欄位的月份值。

SQL> select first_name, extract(month from hire_date) hire_month from employees where last_name = 'Rowe';

FIRST_NAME           HIRE_MONTH
-------------------- ----------
Scott                         9

函數 DATEDIFF在Oracle中不起作用

請注意,您在MySQL中使用的某些日期時間函數,如DATEDIFFYEARMONTHNOWSUBSTRING,在Oracle中不是有效的函數或識別字。您可以查看Oracle SQL語言參考:函數,以防止ORA-00904。

3. 由於拼寫錯誤的欄位而導致的ORA-00904

第三種情況是選擇拼寫錯誤的欄位名稱,這是ORA-00904最常見的模式。

SQL> select first name, last_name from all_names_1 where first_name = 'Scott';
select first name, last_name from all_names_1 where first_name = 'Scott'
       *
ERROR at line 1:
ORA-00904: "FIRST": invalid identifier

在SQL語句中,我故意通過錯過FIRST和NAME之間的底線使欄位名無效。因此,SQL解析器將語句翻譯為:

從表ALL_NAMES_1中查詢名為FIRST的欄位並顯示為NAME,和欄位LAST_NAME以及其他條件。
當然,沒有名為FIRST的有效欄位,甚至沒有First Name。有效且真實的識別字是FIRST_NAME。我們應該再次檢查拼寫,然後更正識別字。

為避免欄位名稱出現拼寫錯誤,您可以使用SQL Developer,Toad for Oracle或PL/SQL Developer等GUI工具來方便您自動填充欄位名。有關SQL Developer的示例:

SQL Developer Editor中的自動填充欄位名稱,以避免ORA-00904無效的識別字
SQL Developer Editor中的自動填充欄位名稱,以避免ORA-00904無效的識別字
正如您所看到的,我們提供了一些字母,SQL開發人員的編輯將負責其餘的工作。

4. 區分大小寫的欄位

在某些情況下,SQL解析器通過拋出ORA-00904來抱怨缺少的欄位,但表中存在欄位。怎麼會發生這種情況?您需要知道的是如何使用精確的表單來表達SQL語句中的欄位。

要使用確切形式的識別字,我們必須使用雙引號來包裝欄位名,這會通知資料庫創建我們提供的確切名稱。究竟怎麼樣?至少,我們應該將它們視為區分大小寫的識別字。

SQL> create table all_names_2 ("First_Name" varchar2(25), "Last_Name" varchar2(25));

Table created.

然後我們插入一些資料。

SQL> insert into all_names_2 select distinct first_name, last_name from employees;

107 rows created.

從現在開始,我們再也不能像過去那樣鬆散地使用表格了。否則,我們很有可能在語句中使用無效識別字,然後看到ORA-00904。

如果不在欄位上添加雙引號,我們就得到了ORA-00904。

SQL> select First_Name, Last_Name from all_names_2 where First_Name = 'Scott';
select First_Name, Last_Name from all_names_2 where First_Name = 'Scott'
                                                    *
ERROR at line 1:
ORA-00904: "FIRST_NAME": invalid identifier
SQL> insert into all_names_2 (First_Name, Last_Name) values ('Scott', 'Rowe');
insert into all_names_2 (First_Name, Last_Name) values ('Scott', 'Rowe')
                                     *
ERROR at line 1:
ORA-00904: "LAST_NAME": invalid identifier

儘管欄位名與其定義完全相同,但由於欄位上缺少雙引號,我們仍然得到ORA-00904。這是因為未引用的識別字First_Name被鬆散地識別為FIRST_NAME,這是一個大寫的識別字。因此,SQL解析器無法在表中找到匹配的識別字。最終,它提出了ORA-00904以提醒這個錯誤的欄位。

解決方法

解決方法很簡單,我們應該按照我們在創建表格時提供的方式引用它們,而不是非引用形式。

SQL> select "First_Name", "Last_Name" from all_names_2 where "First_Name" = 'Scott';

First_Name                Last_Name
------------------------- -------------------------
Scott                     Rowe
SQL> insert into all_names_2 ("First_Name", "Last_Name") values ('Scott', 'Rowe');

1 row created.

我們使用確切的表單來使語句有效。我們可以看到,使用精確的表單非常不方便,我們應該關注識別字的每一個細節,以防止它們被無效。

5. 欄位名稱中的空白

值得注意的是,確切的形式允許我們創建填充空白的欄位,這些欄位在沒有ORA-00904失效問題的情況下有效。讓我們先看一下普通表。

SQL> create table all_names_3 (First_Name varchar2(25), Last_Name varchar2(25), Num int, Create_Date date default sysdate);

Table created.

SQL> insert into all_names_3 (first_name, last_name, num) select first_name, last_name, count(*) from employees group by first_name, last_name;

107 rows created.

SQL> select first_name, last_name, num, create_date from all_names_3 where first_name = 'Scott';

FIRST_NAME                LAST_NAME                        NUM CREATE_DA
------------------------- ------------------------- ---------- ---------
Scott                     Rowe                               1 12-MAR-19

接下來,讓我們看一個奇怪但有效的案例,欄位名中有空格。

SQL> create table all_names_4 ("First_Name" varchar2(25), "Last_Name" varchar2(25), " " int, "  " date default sysdate);

Table created.

SQL> insert into all_names_4 ("First_Name", "Last_Name", " ") select first_name, last_name, count(*) from employees group by first_name, last_name;

107 rows created.

SQL> select "First_Name", "Last_Name", " ", "  " from all_names_4 where "First_Name" = 'Scott';

First_Name                Last_Name
------------------------- ------------------------- ---------- ---------
Scott                     Rowe                               1 12-MAR-19

我們可以看到,我為第三欄位使用了一個空格,第四欄位使用了兩個空格,只要您按照規則查詢表,它們就可以在沒有ORA-00904的情況下正常工作。

有任何名稱衝突或失效?沒有,這是因為一個空白與同一個表的命名空間中的兩個空格不同,特別是當我們使用精確形式來定義欄位時。

即使我們沒有得到任何ORA-00904和無效問題,因為我們仔細而恰當地使用了表格,但確切風格的命名確實令人困惑。嘗試描述奇怪但有效的表格:

SQL> desc all_names_4;
 Name                                      Null?    Type
 ----------------------------------------- -------- ----------------------------
 First_Name                                         VARCHAR2(25)
 Last_Name                                          VARCHAR2(25)
                                                    NUMBER(38)
                                                    DATE

因此,它在第三和第四欄位上顯示的資訊很少。對於一個新成員,他完全不知道這裡發生了什麼。此外,一旦查詢這樣一個奇數表時拋出ORA-00904,沒有人能夠對其進行故障排除。

這提醒我,我曾嘗試在Unix作業系統中刪除空名或空白名稱的檔。我花了很長時間才解決它。

B. WHERE,ORDER BY或GROUP BY中的ORA-00904

我們上面討論的不匹配的欄位問題(如不存在的欄位不存在的函數拼寫錯誤的欄位區分大小寫的欄位)也可能發生在WHEREORDER BYGROUP BY子句中。

在本節中,我們將特別討論如何在WHEREGROUP BY子句中使用欄位別名。

  1. 濫用欄位別名

1. 由於濫用欄位別名而導致的ORA-00904

您可以在ORDER BYORDER BY子句中使用欄位別名,如下所示。

SQL> column did format 9999;
SQL> column eid format 9999;
SQL> select department_id as did, employee_id as eid from employees order by did;

  DID   EID
----- -----
   10   200
   20   201
...

但是,您既不能直接在WHERE子句中使用欄位別名:

SQL> select department_id as did, employee_id as eid from employees where did > 50;
select department_id as did, employee_id as eid from employees where did > 50
                                                                     *
ERROR at line 1:
ORA-00904: "DID": invalid identifier

也不能在GROUP BY子句中使用:

SQL> select department_id as did, count(employee_id) as cnt from employees group by did;
select department_id as did, count(employee_id) as cnt from employees group by did
                                                                               *
ERROR at line 1:
ORA-00904: "DID": invalid identifier

我們都知道欄位DID是什麼,但SQL解析器並不知道。它拋出ORA-00904來提醒問題。

解決方案

當然,您可以使用實際欄位名來隨時抑制ORA-00904。這種方法會更加穩定。

為了能夠在WHERE子句中使用欄位別名,您應該通過外部SELECT包裝查詢。

SQL> select * from (select department_id as did, employee_id as eid from employees) where did > 50;

  DID   EID
----- -----
   90   100
   90   101
...

對於想要使用欄位別名的GROUP BY子句,這有點棘手。

SQL> select did, count(eid) cnt from (select department_id as did, employee_id eid from employees) group by did;

  DID        CNT
----- ----------
  100          6
   30          6
...

也就是說,如果您堅持使用欄位別名,則外部SELECT是此錯誤模式中ORA-00904的解決方案,它可以將所有欄位別名視為實際欄位名。

某些SELECT子條款中,欄位別名c_alias有更多微妙的用法,例如search_clausecycle_clauseorder_by_clause。.

C. CREATE TABLE中的ORA-00904

CREATE TABLE語句中有幾種可能的ORA-00904模式。

  1. 濫用保留字
  2. 錯誤地添加了額外的逗號
  3. 以數字開始

1. 由於濫用保留字而導致的ORA-00904

像ORA-00904這樣的錯誤可能發生在各種物件創建中。讓我們看一些錯誤類型的識別字來闡明命名規則。

使用保留字是瘋狂的,涉及它們的一切可能最終變得不可預測和令人討厭。您永遠不應該使用它們來命名資料庫物件。

SQL> create table t1 (audit int);
create table t1 (audit int)
                 *
ERROR at line 1:
ORA-00904: : invalid identifier

我們再次看到了ORA-00904,但這次SQL解析器無法告訴我們欄位名,並將無效字串留空。

SQL> create table t1 ("audit" int);

Table created.

有可能,您的用戶可能會在完全無意識的情況下創建此類資料庫物件。這是因為他們的工具可以處理剩下的工作。

2. 由於錯誤地添加了額外的逗號而導致的ORA-00904

在語句中錯誤地添加了一個額外的逗號使得SQL解析器不知道該怎麼做,讓我們看看一些例子:

SQL> create table t1 (c1 number, c2 date,);
create table t1 (c1 number, c2 date,)
                                    *
ERROR at line 1:
ORA-00904: : invalid identifier
SQL> create table t1 (c1 number,, c2 date);
create table t1 (c1 number,, c2 date)
                           *
ERROR at line 1:
ORA-00904: : invalid identifier

如您所見,欄位的列表中有一個額外的逗號。SQL解析器知道額外逗號後面並沒有任何內容,但它最終留下ORA-00904讓您去修復這些無效的使用。

正如我們所說的那樣,只要您使用確切的表單來創建表,使用純空格定義欄位是可接受且有意義的。但是,沒有任何內容則是另一個想法,這完全是無稽之談。難怪ORA-00904被拋出。

要解決此問題,我們應刪除額外的逗號以使該語句有效。

SQL> create table t1 (c1 number, c2 date);

Table created.

3. 由於以數位開始而導致的ORA-00904

一個以數字開頭的表名會怎麼樣?

SQL> create table t1 (12345678 int);
create table t1 (12345678 int)
                 *
ERROR at line 1:
ORA-00904: : invalid identifier

ORA-00904警告你,這在這裡是非法的。所以我在識別字之前添加了一個字母“c”來修復ORA-00904。

SQL> create table t1 (c12345678 int);

Table created.

對於正在使用的任何無效字元,會引發ORA-00911以提示此問題,如下所示。

SQL> create table $t1 (c12345678 int);
create table $t1 (c12345678 int)
             *
ERROR at line 1:
ORA-00911: invalid character

實際上,美元符號“$”對於識別字是有效的,只是不要將它放在物件名稱的開頭。有關特殊字元限制的更多資訊,您應該選擇下一個規則。

儘管ORA-00911是對象命名的非法用法,但它並不像ORA-00904那樣明顯和具體。現在讓我們來看看如何在物件命名上使用特殊字元。

特殊字元

只允許$,_和#。對於欄位名,使用不可接受的特殊字元“?”引發ORA-00911無效字元。

SQL> create table t1 (c12345678?production int);
create table t1 (c12345678?production int)
                          *
ERROR at line 1:
ORA-00911: invalid character

取代ORA-00904,我們看到ORA-00911通知我們問號是無效字元。所以我將“?”改為“$”,“#”或“_”來糾正問題。

美元符號

SQL> create table t1 (c12345678$production int);

Table created.

數位標誌

SQL> create table t2 (c12345678#production int);

Table created.

底線

SQL> create table t3 (c12345678_production int);

Table created.

實際上,使用字串作為識別字是很正常的。而不是空格,經常使用底線並建議用於分隔字串中有意義的單詞。

D. ALTER TABLE中的ORA-00904

類似的問題不存在的欄位不存在的功能拼寫錯誤的欄位區分大小寫欄位,在這裡也適用。因此,我寧願在本節討論一些罕見的情況。

ALTER TABLE語句中有幾種ORA-00904模式。

  1. ALTER TABLE ADD 欄位
  2. ALTER TABLE MODIFY 欄位
  3. ALTER TABLE ADD CONSTRAINT NOT NULL

1. ORA-00904在ALTER TABLE ADD 欄位中

ALTER DATABASE ADD欄位語句中的典型ORA-00904 如下所示:

SQL> alter table t1 add column c2 date;
alter table t1 add column c2 date
                   *
ERROR at line 1:
ORA-00904: : invalid identifier

ORA-00904專門定位在保留字COLUMN並告訴您它不是有效的識別字。實際上,這是一個語法錯誤。您不必在語句中添加保留字COLUMN。所以我們通過刪除關鍵字來糾正它。

SQL> alter table t1 add c2 date;

Table altered.

此外,在ADD之後,您不應該在該位置使用任何保留字。

2. ORA-00904在ALTER TABLE MODIFY 欄位中

讓我們在ALTER DATABASE MODIFY欄位語句中看一種ORA-00904的情況。

SQL> alter table all_names_1 modify (column fname varchar2(30));
alter table all_names_1 modify (column fname varchar2(30))
                                *
ERROR at line 1:
ORA-00904: : invalid identifier

同樣的原因,您不必在語句中添加保留字COLUMN。請刪除它。

刪除保留字後,我們仍然得到了ORA-00904,這是因為我故意使用了無效的欄位名。

SQL> alter table all_names_1 modify (fname varchar2(30));
alter table all_names_1 modify (fname varchar2(30))
                                *
ERROR at line 1:
ORA-00904: "FNAME": invalid identifier

表格中未找到欄位FNAME。有效的欄位名稱應為FIRST_NAME

SQL> alter table all_names_1 modify (first_name varchar2(30));

Table altered.

3. ORA-00904在ALTER TABLE ADD CONSTRAINT NOT NULL中

SQL> create table t1 (c1 number);

Table created.

您可以在ALTER TABLE ADD CONSTRAINT語句中的欄位上添加UNIQUE約束,如下所示:

SQL> alter table t1 add constraint c1_unique UNIQUE (c1);

Table altered.

但是您不能以相同的方式在欄位上添加NOT NULL約束。

SQL> alter table t1 add constraint c1_nn NOT NULL (c1);
alter table t1 add constraint c1_nn NOT NULL (c1)
                                    *
ERROR at line 1:
ORA-00904: : invalid identifier

如您所見,SQL解析器拋出ORA-00904以警告語句中使用的識別字名稱是非法的。實際上,這是一個語法錯誤。

為什麼?NOT NULL是一個約束,不是嗎?當然,NOT NULL是某種約束,但它更像是一個欄位屬性,我們以錯誤的方式使用它。我們先把它當作約束。

解決方案1:將其視為約束

基本上,Oracle中約束子句有4種子條款

  • inline_constraint
  • out_of_line_constraint
  • inline_ref_constraint
  • out_of_line_ref_constraint

在上面生成ORA-00904的語句中,它是一個out_of_line_constraint子句,它不允許使用NOT NULL。相反,您必須將inline_constraint用於NOT NULL。這就是你在添加約束NOT NULL時看到ORA-00904的原因。

SQL> alter table t1 modify (c1 constraint c1_nn NOT NULL);

Table altered.

我們來檢查約束名稱。

SQL> select constraint_name from user_constraints where table_name = 'T1';

CONSTRAINT_NAME
------------------------------
C1_UNIQUE
C1_NN

SQL> alter table t1 drop constraint C1_NN;

Table altered.

與其他約束不同,NOT NULL不能是複合(多欄位)約束,它僅用於其欄位。

解決方案2:將其視為欄位屬性

嚴格地說,NOT NULL是一個欄位屬性,因此您不必將其視為約束,即便它可以是約束。

例如,我們可以將欄位修改為NOT NULL,如下所示:

SQL> alter table t1 modify (c1 NOT NULL);

Table altered.

我們可以看到,我將它視為欄位屬性,而不涉及任何約束子句。我們來檢查約束名稱。

SQL> select constraint_name from user_constraints where table_name = 'T1';

CONSTRAINT_NAME
------------------------------
C1_UNIQUE
SYS_C0011427

因此,資料庫為約束提供了系統生成的名稱。讓我們進一步看看我們如何放棄約束。

SQL> alter table t1 modify (c1 NULL);

Table altered.

SQL> select constraint_name from user_constraints where table_name = 'T1';

CONSTRAINT_NAME
------------------------------
C1_UNIQUE

也就是說,我們不必知道約束名稱就可以刪除它,只需恢復屬性即可。

E. PL/SQL中的ORA-00904

到目前為止,我們在PL/SQL中有兩個錯誤模式ORA-00904。

  1. PL/SQL中的變數聲明順序不正確
  2. 不帶引號的字串

1. 由於PL/SQL中的變數聲明順序不正確而導致的ORA-00904

假設我們想使用一個涉及這樣的變數的游標:

SQL> declare
  2    cursor c1 is select employee_id from hr.employees where department_id = v_num;
  3    v_num number;
  4  begin
  5    v_num := 110;
  6    open c1;
  7  end;
  8  /
  cursor c1 is select employee_id from hr.employees where department_id = v_num;
                                                                          *
ERROR at line 2:
ORA-06550: line 2, column 75:
PLS-00320: the declaration of the type of this expression is incomplete or
malformed
ORA-06550: line 2, column 75:
PL/SQL: ORA-00904: "V_NUM": invalid identifier

ORA-06550: line 2, column 16:
PL/SQL: SQL Statement ignored

我們看到了PL/SQL引擎拋出的ORA-00904。其中,ORA-06550表示第2列第75行的識別字在匿名PL/SQL塊中被非法使用。

這個錯誤非常明顯,我們在聲明它們之前不能使用變數。換句話說,我們必須先聲明變數。所以我交換第2和第3行:

SQL> declare
  2    v_num number;
  3    cursor c1 is select employee_id from hr.employees where department_id = v_num;
  4  begin
  5    v_num := 110;
  6    open c1;
  7  end;
  8  /

PL/SQL procedure successfully completed.

2. 由於不帶引號的字串而導致的ORA-00904

在PL/SQL中使用EXECUTE IMMEDIATE時,您可能想知道如何在語句中引用字串。

SQL> begin
  2    execute immediate 'select nvl(first_name, NO_VALUE) from employees';
  3  end;
  4  /
begin
*
ERROR at line 1:
ORA-00904: "NO_VALUE": invalid identifier
ORA-06512: at line 2

在上面的語句中,我們想用函數NVLNO_VALUE字串替換所有NULL值,但我們猶豫是在語句中引用字串,該語句現在也是一個字串。結果,我們得到了ORA-00904。現在問題是,如何引用外部字串中的字串以使其正確?

解決方案

答案是,只需將每個單引號複製為兩個單引號,以便在字串中轉義單個引號,無論您希望在另一個字串中顯示字串,尤其是在EXECUTE IMMEDIATE中。

SQL> begin
  2    execute immediate 'select nvl(first_name, ''NO_VALUE'') from employees';
  3  end;
  4  /

PL/SQL procedure successfully completed.

現在代碼塊很好。

Leave a Reply

Your email address will not be published. Required fields are marked *