存储在VARCHAR2变量中的查询结果不会被视为空字符串或NULL?-Oracle PL/SQL-Oracle 11g
我有一个执行SELECT INTO的过程,并将返回的结果存储在名为存储在VARCHAR2变量中的查询结果不会被视为空字符串或NULL?-Oracle PL/SQL-Oracle 11g,oracle,plsql,oracle11g,ora-06512,ora-06502,Oracle,Plsql,Oracle11g,Ora 06512,Ora 06502,我有一个执行SELECT INTO的过程,并将返回的结果存储在名为account\uu的VARCHAR2变量中: SELECT DISTINCT NVL(XYZ_API.Get_Ref(company, currency, pay_type, order_id), XYZ_API.Get_Id(company, currency, pay_type, order_id)) account INTO account_ FROM some_table WHE
account\uu
的VARCHAR2变量中:
SELECT DISTINCT NVL(XYZ_API.Get_Ref(company, currency, pay_type, order_id),
XYZ_API.Get_Id(company, currency, pay_type, order_id)) account
INTO account_
FROM some_table
WHERE company = company_
AND payment_type = 'SUPP'
AND order_id = order_id_
AND payment_date = pay_date_;
公司
、订单
和付款日期
都是我用来过滤记录的VARCHAR2变量
然后将纳入账户的结果格式化如下,并存储在另一个名为giro\ucode>的VARCHAR2变量中:
giro:=LPAD(翻译(account_uu,'1234567890-','1234567890'),16,'0')代码>
然后我检查giro\uu
是否是一个数字,如下所示,使用FOR循环
FOR i_ IN 1..LENGTH( giro_ ) LOOP
c_ := ASCII( SUBSTR( giro_ , i_, 1 ) );
IF ( c_ < ASCII( '0' ) OR c_ > ASCII( '9' ) ) THEN
RETURN FALSE;
END IF;
END LOOP;
用于1.长度(giro)循环中的i_uuu
c_:=ASCII(SUBSTR(giro_,i_,1));
如果(cASCII('9')),则
返回FALSE;
如果结束;
端环;
我有一个场景,上面显示的SELECT查询不会拾取任何记录
这最终在FOR循环中引入了一个异常,错误为ORA-06502和ORA-06512
据我了解,原因是长度(giro)
1..LENGTH(giro_)
失败,因为giro_
值(长度为空)的长度无法转换为数字
我的问题是,在这个场景中,giro\ucode>是空字符串还是空字符串?
这里到底发生了什么
谢谢 你的理解是错误的LENGTH
将始终返回一个数字(字符串长度),它不会检查其参数是否为数字
该规则的例外情况是,如果其(LENGTH
)参数是空字符串(在Oracle中,它等于NULL
)-则长度也是未知的(NULL
):
在这种情况下,请修改代码,使其包含NVL
功能,例如:
FOR i_ IN 1 .. NVL(LENGTH( giro_ ), 0) LOOP
对于空字符串,它不会做任何事情。虽然我逐渐意识到空字符串和NULL在Oracle中是相同的,LENGTH
是极少数的缺点之一。如果是空字符串,则返回NULL而不是零。奇怪的是,您看到了使用DISTINCT
的必要性,但却看到它保证只得到一个结果行。这可能表明数据模型不好或查询不太可靠。是的,我同意你的说法。我将尝试修改我的数据/查询:)谢谢您的输入!嗨,谢谢你的回答。我想你同意我在这个问题上的观点了吧?当我说“1..LENGTH(giro_uu)失败,因为giro_u值的长度无法转换为数字”时,我的意思是代码失败,因为LENGTH的返回值在这里为NULL。所以,循环不能从1变为NULL,它应该是1到某个数字。不客气。很抱歉,如果我误解了你说的话。
FOR i_ IN 1 .. NVL(LENGTH( giro_ ), 0) LOOP