Oracle ORA-01403:找不到数据为什么?

Oracle ORA-01403:找不到数据为什么?,oracle,plsql,database-metadata,execute-immediate,Oracle,Plsql,Database Metadata,Execute Immediate,我已宣布以下程序: CREATE OR REPLACE PROCEDURE MODIFY_NOT_NULL( v_tbName IN VARCHAR2, v_cName IN VARCHAR2, v_defaultValue IN VARCHAR2 ) IS v_is_null VARCHAR2(1); BEGIN SELECT nullable INTO v_is_null FR

我已宣布以下程序:

 CREATE OR REPLACE PROCEDURE MODIFY_NOT_NULL(
      v_tbName       IN VARCHAR2,
      v_cName        IN VARCHAR2,
      v_defaultValue IN VARCHAR2 )
   IS
      v_is_null VARCHAR2(1);
   BEGIN

      SELECT nullable INTO v_is_null 
      FROM USER_TAB_COLUMNS 
      WHERE TABLE_NAME = v_tbName 
      AND COLUMN_NAME  = v_cName;

      IF  v_is_null   = 'Y' THEN
          EXECUTE IMMEDIATE ('ALTER TABLE ' || v_tbName 
               || ' MODIFY (' || v_cName 
               || ' DEFAULT ' || v_defaultValue 
               || '  NOT NULL )');
      END IF;
   END;
但是,当我执行代码时:

BEGIN
   modify_not_null('TABLE_NAME', 'COLUMN_NAME ' ,'0');
END;
/ 
我得到一份工作

ORA-01403:未找到任何数据

如果SELECT INTO语句不返回任何值,通常会引发此异常,但是执行此操作时,我将始终获得一个值:

Select nullable 
from USER_TAB_COLUMNS 
WHERE table_name = 'TABLE_NAME' 
AND column_name  = 'COLUMN_NAME';

当我执行上面的代码时,结果是N或Y。所以我总是得到一个结果。我不知道为什么会抛出此异常

您正在将v_defaultValue param传递给列名

将程序更改为

SELECT nullable INTO v_is_null 
FROM USER_TAB_COLUMNS 
WHERE TABLE_NAME = v_tbName AND COLUMN_NAME  = v_cName ;

您正在将v_defaultValue参数传递给列名

将程序更改为

SELECT nullable INTO v_is_null 
FROM USER_TAB_COLUMNS 
WHERE TABLE_NAME = v_tbName AND COLUMN_NAME  = v_cName ;

您的呼叫包含尾随空格:

modify_not_null('TABLE_NAME', 'COLUMN_NAME ' ,'0');
                                          ^
因此proc未找到任何数据,因为“COLUMN_NAME”!='列名称'


使用uppertrimv_cName防止打字错误导致错误。应用于所有参数。

您的呼叫包含尾随空格:

modify_not_null('TABLE_NAME', 'COLUMN_NAME ' ,'0');
                                          ^
因此proc未找到任何数据,因为“COLUMN_NAME”!='列名称'

使用uppertrimv_cName防止打字错误导致错误。应用于所有参数。

在选择之前。。。。在这种情况下,你必须确保有一些东西可以选择。因为根据您是什么用户以及您提供的参数,表中可能没有数据

一种简单的方法是在选择之前的开始处有一个计数:

在您选择….之前,请共享并享受。。。。在这种情况下,你必须确保有一些东西可以选择。因为根据您是什么用户以及您提供的参数,表中可能没有数据

一种简单的方法是在选择之前的开始处有一个计数:

分享和享受

保持优雅:

create or replace procedure modify_not_null(v_tbName       in varchar2,
                                            v_cName        in varchar2,
                                            v_defaultValue in varchar2) is
  cursor c_tbl(cp_tbname in varchar2, 
               cp_cname in varchar2) is
    select nullable
      from user_tab_columns
     where table_name  = upper(cp_tbname)
       and column_name = upper(cp_cname);

  l_tbl c_tbl%rowtype;
begin

  open c_tbl(cp_tbname => v_tbName,
             cp_cname => v_cName);
  fetch c_tbl into l_tbl;
  close c_tbl;

  if l_tbl.nullable = 'Y' then
    execute immediate 'alter table ' || v_tbName || ' modify (' || v_cName ||
                      ' default ' || v_defaultValue  || '  not null )';
  end if;
exception
  when others then
    raise_application_error(-20000, dbms_utility.format_error_stack);
end modify_not_null;
保持优雅:

create or replace procedure modify_not_null(v_tbName       in varchar2,
                                            v_cName        in varchar2,
                                            v_defaultValue in varchar2) is
  cursor c_tbl(cp_tbname in varchar2, 
               cp_cname in varchar2) is
    select nullable
      from user_tab_columns
     where table_name  = upper(cp_tbname)
       and column_name = upper(cp_cname);

  l_tbl c_tbl%rowtype;
begin

  open c_tbl(cp_tbname => v_tbName,
             cp_cname => v_cName);
  fetch c_tbl into l_tbl;
  close c_tbl;

  if l_tbl.nullable = 'Y' then
    execute immediate 'alter table ' || v_tbName || ' modify (' || v_cName ||
                      ' default ' || v_defaultValue  || '  not null )';
  end if;
exception
  when others then
    raise_application_error(-20000, dbms_utility.format_error_stack);
end modify_not_null;


为什么将数据选择到v_is_null中,但如果条件为l_null,则可以?可能是l_nullable是声明的局部变量,但已初始化。非常抱歉,我的帖子中再次出现了错误…不幸的是,这不是错误,但对于您从不同用户执行查询和PL SQL块的hintAre来说,thx非常重要?如果用户id不同,则用户选项卡列中的数据会更改。最好的调试方法是在代码中的每一行后面都放一个dbms_输出,以了解异常的起源。不,我只与一个用户一起执行。子程序调用参数中有一个额外的空间:“COLUMN_NAME”为什么选择v_中的数据为空,但如果条件为l_可空?可能是l_nullable是声明的局部变量,但已初始化。非常抱歉,我的帖子中再次出现了错误…不幸的是,这不是错误,但对于您从不同用户执行查询和PL SQL块的hintAre来说,thx非常重要?如果用户id不同,则用户选项卡列中的数据会更改。最好的调试方法是在代码中的每一行后面放一个dbms_输出,以了解异常的起源。不,我只与一个用户一起执行。在子程序调用参数中有一个额外的空间:“COLUMN_NAME”@APC,是的,是的,我的错误。我测试了,但错了“:/。。。我又回到了我的第一个答案。@APC,是的,对了,我错了。我测试了,但错了“:/。。。我回到了我的第一个答案。看起来OP的错误是由于参数中的尾随空格造成的,而您所有的额外代码实际上并没有解决这个问题。这如何解决OP的问题?如果原始代码引发ORA-01403,除了隐藏异常发生的真实位置之外,此代码将遇到完全相同的问题。OP问题是什么?如果找不到表,它不会引发任何错误。它不会受到ORA-01403的影响,请在说不明智的话之前尝试。抑制错误消息与修复问题不同。OP的错误似乎是由于参数中的尾随空格造成的,你所有的额外代码都不能解决这个问题。这怎么解决OP的问题呢?如果原始代码引发ORA-01403,除了隐藏异常发生的真实位置之外,此代码将遇到完全相同的问题。OP问题是什么?如果找不到该表,它将不会引发任何错误。它不会受到ORA-01403的影响,在说不明智的话之前尝试一下。抑制错误消息与修复问题不同。