oracle 让人抓狂的错误之 null值 与 无值(无结果)-开发系列(一)
2016-01-01 21:24
435 查看
近期。在做开发、写存过的时候碰到一些问题,找了好长时间才发现原因。并且是曾经不知道的。
所以在这给记下来 给自己备忘和大家參考。
![](https://oscdn.geek-share.com/Uploads/Images/Content/201601/10efa109cc1f880b094c91d43dde29c0)
上面是一个非常easy表的全部数据。area_num 区域编码 area_name 区域名称 delflag 有无效标识 1有效 0无效(当中淮北 和宣城的delflag为null)。
如今想找出有效的那些区域信息,所以用以下的语句:
![](https://oscdn.geek-share.com/Uploads/Images/Content/201601/9c49d39e07672db6dd2edbfb86bad31d)
上面的结果中没有淮北和宣城 跟预想中的不一样 一開始以为是 delflag不为0的全部应该都被查询出来 包含淮北和宣城。
其实 淮北和宣城 delflag的字段是 null值。在oracle里面null值得概念:
NULL是数据库中特有的数据类型,当一条记录的某个列为NULL,则表示这个列的值是未知的、是不确定的。
既然是未知的,就有无数种的可能性。因此。NULL并非一个确定的值。
所以null值(不确定的值) 并不符合 !='0' 这个 条件。相同以下语句也是这样。
![](https://oscdn.geek-share.com/Uploads/Images/Content/201601/00c88fe8bff89d8b8130f9a4a356d727)
结果为null:
![](https://oscdn.geek-share.com/Uploads/Images/Content/201601/768c1443e68e4f3f84a81fe369a57261)
无结果:
![](https://oscdn.geek-share.com/Uploads/Images/Content/201601/9c4454fceeda68b10fa7bef0b8bbc3c2)
表面看非常的清楚明确,可是到了实际应用中可能 会easy搞错。
以下是演示样例的存储过程:
操作日志表的orgid有为空的情况。
if(orgid_var is null) 这个条件 推断假设为空 视该记录无效,不參与推断(业务要求)。
假设不加这个条件 (且没有
以下这个语句
所以在这给记下来 给自己备忘和大家參考。
一 、null值
以下举个最简单的样例。寻常工作其中肯定比这个sql复杂的多,在这仅仅是把这个易错点呈现出来,他可能是一个复杂sql出错的小的 不easy被发现的一个问题。上面是一个非常easy表的全部数据。area_num 区域编码 area_name 区域名称 delflag 有无效标识 1有效 0无效(当中淮北 和宣城的delflag为null)。
如今想找出有效的那些区域信息,所以用以下的语句:
上面的结果中没有淮北和宣城 跟预想中的不一样 一開始以为是 delflag不为0的全部应该都被查询出来 包含淮北和宣城。
其实 淮北和宣城 delflag的字段是 null值。在oracle里面null值得概念:
NULL是数据库中特有的数据类型,当一条记录的某个列为NULL,则表示这个列的值是未知的、是不确定的。
既然是未知的,就有无数种的可能性。因此。NULL并非一个确定的值。
所以null值(不确定的值) 并不符合 !='0' 这个 条件。相同以下语句也是这样。
二、无结果
无结果事实上就是一个select查询没有结果集(不是null,而是没有结果)结果为null:
无结果:
表面看非常的清楚明确,可是到了实际应用中可能 会easy搞错。
以下是演示样例的存储过程:
create or replace function getProceessidAllDealBySkf_l(proceessid in number) return varchar2 as cursor pcursor is( select distinct t.orgid, t.oper_name from tssa_his_dsg.wh_common_busilog_td t where t.processinstid = proceessid);--取操作日志表某个工单流程proceessid的操作人所属机构id。和操作名称 orgidCursor pcursor%rowtype;--定义类型为pcursor行数据的 变量 orgid_var varchar2(20);--存放操作人机构id变量 returnflag varchar2(20);--返回的标志位 orgseqflag varchar2(50);--操作人机构id及其全部父id 串起来字符 skforgflag varchar2(20);--存放操作人机构id变量 count_var number;--存放统计数字变量 oper_name_var varchar2(100);--操作名称 begin returnflag := '1';--返回值初始化为1 orgseqflag := null;--初始化 skforgflag := null;--初始化 count_var := 0;--初始化 oper_name_var := null;--初始化 open pcursor;--打开游标 loop fetch pcursor into orgidCursor;--把游标数据放进pcursor变量 exit when pcursor%notfound; orgid_var := orgidCursor.orgid;--从orgidCursor变量取值到orgid_var oper_name_var := orgidCursor.oper_name;--从orgidCursor变量取值到oper_name_var if (orgid_var is null) then--orgid_var是可能为空的 表里面t.orgid为空 null; else select count(1) into count_var from tssa_dsg.eosorg_t_organization b, (select a.* from tssa_dsg.bndict_t_dictionary a where a.BUSINTYPEID = 'WH_CH_ORAPROPERTY' and a.status = '0') a where b.orgproperty = a.businid(+) and b.orgid = orgid_var;--统计操作日志表的机构id是否在机构静态表里 if (count_var > 0) then--在里面 select t.orgseq into orgseqflag from tssa_dsg.eosorg_t_organization t where t.orgid = orgid_var --取orgseqflag ; select a.businname into skforgflag from tssa_dsg.eosorg_t_organization b, (select a.* from tssa_dsg.bndict_t_dictionary a where a.BUSINTYPEID = 'WH_CH_ORAPROPERTY' and a.status = '0') a where b.orgproperty = a.businid(+) and b.orgid = orgid_var;--取组织分类 if (orgseqflag like '99999.7676.%' or skforgflag = '省客服' or (skforgflag != '省客支' and skforgflag != '省层面' and oper_name_var = '话务员追加信息')) then null; else returnflag := null;--不满足id条件 置返回值为null end if; end if; end if; end loop; close pcursor; return returnflag; end;上面这个过程的作用就是根工单流程id 返回该工单是否仅仅经过某个特定组织机构的人处理的标志。
操作日志表的orgid有为空的情况。
if(orgid_var is null) 这个条件 推断假设为空 视该记录无效,不參与推断(业务要求)。
假设不加这个条件 (且没有
select count(1) into count_var from tssa_dsg.eosorg_t_organization b, (select a.* from tssa_dsg.bndict_t_dictionary a where a.BUSINTYPEID = 'WH_CH_ORAPROPERTY' and a.status = '0') a where b.orgproperty = a.businid(+) and b.orgid = orgid_var;--统计操作日志表的机构id是否在机构静态表里)
以下这个语句
select t.orgseq into orgseqflag from tssa_dsg.eosorg_t_organization t where t.orgid = orgid_var查出来是没有结果的 就是无值
into orgseqflag就会报错(调试会报错,直接执行不报错) 直接 跳出 loop 给 return 一个null 值 是不符合业务要求的。
select count(1) into count_var from tssa_dsg.eosorg_t_organization b, (select a.* from tssa_dsg.bndict_t_dictionary a where a.BUSINTYPEID = 'WH_CH_ORAPROPERTY' and a.status = '0') a where b.orgproperty = a.businid(+) and b.orgid = orgid_var;--统计操作日志表的机构id是否在机构静态表里上面这个条件作用跟if(orgid_var is null)是一样的 是忽略 操作日志表的机构id不在机构静态表里的情况。
if (count_var > 0) then--在里面
相关文章推荐
- oracle数据库文件系统迁移到ASM
- oracle linux6操作系统oracle11.2.0.4数据库从一台主机A(ora11g)到另一台主机B(ora02)的迁移过程
- 数据库索引原理(oracle10g宝典17章读书笔记)
- Oracle raw数据类型
- oracle删除用户和表空间
- AIX环境下oracle重启
- oracle表空间自动扩展
- ORACLE ORA-01653: unable t…
- 卸载 Oracle 的 JDK
- Oracle 11g R2安装手册(图文教程)For Windows
- 大表添加字段时需要注意default问题
- ORACLE 重做日志
- 【翻译自mos文章】在Oracle单机数据库中定义database service
- ORACLE ROWNUM解析[转]
- Oracle表分区
- Oracle高级查询,GROUP BY
- Oracle高级查询,over 用法
- 完全卸载oracle11g
- Oracle用imp导入出现ora-20000错误
- Oracle job procedure