ORA-06502: PL/SQL: 数字或值错误
大家好:
今天我设计了一个存储过程,用了动态语句。发现了上面的错误,并找到了相应的解决方法。发表出来,希望别人少走弯路。
我用的是直接执行语句的形式,关键代码如下所示:
说明一点:VI_DATE是过程的输入参数
EXECUTEIMMEDIATE'INSERT /*+append*/ INTO KR_114_ORDER_ALL NOLOGGING
(STATICE_MONTH, --月份
TELE_TYPE, --业务类型
TOTAL_SUM, --当月收入
USER_CNT --当月用户数
)
--插入酒店业务
SELECT /*+FIRST_ROWS*/
'''||VI_DATE||''', --月份
''02'', --业务类型
SUM(T.TOTAL_SUM), --当月收入
COUNT(distinct T.DESTINE_TEL) --用户数
FROM dw_hotel_order T
WHERE T.LEAV_DATE LIKE '''||VI_DATE||'%''
AND T.ORDER_TYPE = ''01''
union all
--插入机票业务
SELECT /*+FIRST_ROWS*/
'''||VI_DATE||''', --月份
''03'', --业务类型
SUM(t.settlement_price), --当月收入
COUNT(DISTINCT t.linkman_phono) --用户数
FROM dw_ticket_detail_collect T
WHERE t.date_of_issue LIKE '''||VI_DATE||'%''
AND t.passenger_ticket = ''01''
union all
--插入美食业务
SELECT /*+FIRST_ROWS*/
'''||VI_DATE||''', --月份
''04'', --业务类型
SUM(t.monetary), --当月收入
COUNT(DISTINCT t.roscoe_people_phono) --用户数
FROM dw_cate_rice_detail T
WHERE t.placing_time LIKE '''||VI_DATE||'%''
AND t.order_status = ''01''
union all
--插入蛋糕业务
SELECT /*+FIRST_ROWS*/
'''||VI_DATE||''', --月份
''05'', --业务类型
SUM(t.total_price), --当月收入
COUNT(DISTINCT t.book_phone) --用户数
FROM dw_cake_order T
WHERE t.order_date LIKE '''||VI_DATE||'%''
AND t.order_type_id = ''1''
union all
--插入农产品业务
SELECT /*+FIRST_ROWS*/
'''||VI_DATE||''', --月份
''06'', --业务类型
SUM(t.pay_sum), --当月收入
COUNT(DISTINCT t.destine_tel) --用户数
FROM dw_agriculture_order T
WHERE t.update_time LIKE '''||VI_DATE||'%''
AND t.order_status = ''01''
union all
--插入鲜花业务
SELECT /*+FIRST_ROWS*/
'''||VI_DATE||''', --月份
''07'', --业务类型
SUM(t.total_sum), --当月收入
COUNT(DISTINCT t.destine_tel) --用户数
FROM dw_flower_order T
WHERE t.update_time LIKE '''||VI_DATE||'%''
AND t.order_status = ''01''
union all
--插入杂志业务
SELECT /*+FIRST_ROWS*/
'''||VI_DATE||''', --月份
''09'', --业务类型
SUM(t.one_magazine_price), --当月收入
COUNT(DISTINCT t.link_phone) --用户数
FROM dw_magazine_order T
WHERE t.order_date LIKE '''||VI_DATE||'%''
AND t.order_type_id = ''1''
union all
--插入影讯业务
SELECT /*+FIRST_ROWS*/
'''||VI_DATE||''', --月份
''11'', --业务类型
SUM(t.amount), --当月收入
COUNT(DISTINCT t.phone) --用户数
FROM dw_ticket_movie T
WHERE t.pay_time LIKE '''||VI_DATE||'%''';
过程能跑通,数据质量也没有问题。后来我突发奇想,何不定义一个保存sql语句的变量,直接执行变量就行了。所以,我进行了如下的操作。
V_SQL VARCHAR2(2000);
V_SQL :=’ INSERT /*+append*/ INTO.. LIKE '''||VI_DATE||' %''';
就是把上面写的EXECUTE IMMEDIATE后面的语句全部付给了变量V_SQL
EXECUTEIMMEDIATE V_SQL;
这时,问题出来了。执行过程时,报了“ORA-06502: PL/SQL: 数字或值错误”。这我就很郁闷了,是我的逻辑错误了吗?这是怎么回事呢?
后来我把变量类型修改为varchar2(100000),然后用length函数看看变量的长度,结果显示为2290。这就说明,我定义的变量的长度小了。接下来,我修改为varchar2(3000),就可以了。
总结一下,利用动态语句时,一定要知道要执行的语句长度后再进行定义变量的长度。