为什么 'NOT IN' 运算符不为没有任何值的列获取记录?
Why 'NOT IN' operator not fetching records for the columns which is not having any value?
我有一个 table 的列名为 CORP_SERIOUS,该列的值可以是 1 或 2 或为空。当我使用 NOT IN 运算符搜索 unknown values 记录意味着 empty 字段时,我得到 计数为零。
为什么下面的查询 没有获取 没有 vm.CORP_SERIOUS NOT IN('1','2')
的字段的记录?
这是查询:
SELECT COUNT(*)
FROM
( SELECT DISTINCT vm.vaer_no vaer,
vm.vaer_no_version version,
vm.priority priority,
vm.case_reported_in reportedIn,
vsr.originalreceivedate initialRcvDate,
vsr.mostrecentinfodate latestRcvDate,
vsr.primarysourcecountry reportingCountry,
vsr.occurcountry occurCountry,
vsrd.primary_source_full_name reporterFullName,
vsrd.sender_full_name senderFullName,
vm.record_id recordId,
vm.notes_flag notesFlag,
vm.dmi_product product,
vmf.VAERS_LINKED,
vm.VAER_STATUS status,
vm.company_unit_name companyunit,
FIND_WF_ACTIVITY(vm.record_id,JBPM_PROCESS_INST_ID),
vmf.CORRESPONDENCE_FLAG corresFlag,
vmf.READ_UNREAD_CORRESPONDENCE readUnreadCorresp,
vm.vaer_mode vmode,
srcDoc.doc_name,
vsr.seriousnessdecision serious,
vm.reportduedate reportduedate,
vm.MANUALLY_LOCKED,
vm.LOCKED_BY,
vm.LOCKED_REASON,
vm.LOCKED_DATE,
vm.vaer_delete,
vm.vaer_nullify nullify,
vm.archived,
vm.COMPLETION_FLAG,
vm.ASSIGNED_USER_GROUP,
COALESCE(vsrd.TEEATESPECIESDECODE,vsrd.SPECIESDECODE,vsrd.OTHERSPECIES,vsrd.TREATEDSPECIES),
COALESCE(vsrd.ANIMAL_BREEDDECODE,vsrd.TREATED_BREEDDECODE,vsrd.ANIMAL_BREED,vsrd.TREATED_BREED),
vm.APPROVED_VAER,
vm.SUBSTANCE_ADDED,
vm.MULTIPLEBREEDADDED,
msg_q.MDN_DATE,
vm.CASE_SOURCE,
vm.MESSAGENUMB,
vsr.NULLIFICATIONREASON,
vm.CREATED_BY,
vm.ASSESSMENT_SOURCE,
vm.ASSESSMENT_CLASSIFICATION,
vm.DMI_VEDDRA_TERM,
vsr.CASEREGISTRATIONTYPE,
vm.AUTHORIZATIONCOMPANY,
vm.E2B_DMI_PRODUCT brandname,
vm.E2B_SUBSTANCE_ADDED e2bSubstanceAdded,
vm.ACCOUNT account,
ACK.record_id ack_recId ,
vm.SUBMITTED_DELAY
FROM agvet_vae_info vm,
agvet_vae_safetyreport vsr,
agvet_vae_safetyreport_detail vsrd,
AGVET_VAE_SOURCE_DOC srcDoc,
AGVET_VAE_FLAGS vmf,
E2B_MESSAGE_QUEUE msg_q,
E2B_MESSAGE_ACK ACK
WHERE vm.fk_avsr_rec_id = vsr.record_id
AND vsr.fk_avsrd_rec_id = vsrd.record_id
AND srcdoc.record_id(+) = vm.fk_vet_source_doc_rec_id
AND vm.IMPORT_FLAG <> 1
AND (vm.DRAFT_SUBMIT_FLAG = 0
OR vm.DRAFT_SUBMIT_FLAG = 2)
AND vm.VAER_NO = vmf.VAER_NO(+)
AND vm.E2B_MESSAGE_LIST_TYPE<>01
AND vm.MESSAGENUMB = msg_q.MESSAGE_NUMBER(+)
AND vm.MESSAGENUMB = ACK.MESSAGE_NUMBER(+)
AND (vm.assigned_to = 48626
OR vm.assigned_to IS NULL
OR vm.assigned_to = 320538
OR vm.assigned_to = 320529
OR vm.assigned_to = 406699)
AND EXISTS
(SELECT *
FROM jbpm_token jt
WHERE jt.node_ IN ( 135,140,146,137,132,129,127,148,144 )
AND jt.processinstance_ = vm.jbpm_process_inst_id
OR vm.jbpm_process_inst_id IS NULL
)
AND ( fn_access_vet_products(48658,vm.RECORD_ID, vm.CASE_REPORTED_IN)=1)
AND (vm.PRIORITY IN ( 02 )
OR vm.PRIORITY IS NULL)
AND ( upper(vm.CORP_SERIOUS) NOT IN ('1','2') )
AND vm.ARCHIVED = 0
AND vm.vaer_nullify = 0
AND vm.vaer_delete = 0
)
你可以试试这个查询
convert(varchar(50),vm.CORP_SERIOUS) NOT IN('1','2')
值NULL表示未知。
WHERE vm.CORP_SERIOUS IN('1','2')
- “1”为真
- 对于“3”是假的
- 对于 NULL
是 NULL
和
WHERE vm.CORP_SERIOUS NOT IN('1','2')
- 不正确,因此“1”为错误
- 不是 FALSE,因此对于“3”是 TRUE
- 不是 NULL,对于 NULL
又是 NULL
由于 NULL 表示未知,我们不知道该值(我们不知道)是否在给定的集合中。所以答案是"I don't know",无论我们问值是否在列表中或值是否不在列表中。
假设我们不知道约翰的 phone 号码,我给你看一些号码,然后问你约翰的号码是否在其中。你不能说是,你不能说不是,你只能说也许。与 DBMS 相同。它不能告诉你 TRUE 或 FALSE,它只能告诉你 NULL。现在 WHERE 子句的工作方式如下:查询 returns 给定条件为 TRUE 的所有记录。 NULL 不为 TRUE,因此不返回记录。
(即使 NULL 本身在列表中,我们也不知道集合中的未知值是否与记录中的未知值相同。WHERE 子句仍然会导致 NULL。它会使但是 '3' 的区别:WHERE vm.CORP_SERIOUS NOT IN('1','2', null)
也会突然导致 NULL,因为集合中的未知值可能是也可能不是 '3'。)
你可以问:给我所有未知值加上列表中的值。
WHERE vm.CORP_SERIOUS IS NULL OR vm.CORP_SERIOUS NOT IN('1','2')
或者您可以问:
WHERE NVL(vm.CORP_SERIOUS, 'TREAT AS NOT IN THE LIST') NOT IN('1','2')
(嗯,当然字符串 'TREAT AS NOT IN THE LIST' 不能在列表中:-)
我有一个 table 的列名为 CORP_SERIOUS,该列的值可以是 1 或 2 或为空。当我使用 NOT IN 运算符搜索 unknown values 记录意味着 empty 字段时,我得到 计数为零。
为什么下面的查询 没有获取 没有 vm.CORP_SERIOUS NOT IN('1','2')
的字段的记录?
这是查询:
SELECT COUNT(*)
FROM
( SELECT DISTINCT vm.vaer_no vaer,
vm.vaer_no_version version,
vm.priority priority,
vm.case_reported_in reportedIn,
vsr.originalreceivedate initialRcvDate,
vsr.mostrecentinfodate latestRcvDate,
vsr.primarysourcecountry reportingCountry,
vsr.occurcountry occurCountry,
vsrd.primary_source_full_name reporterFullName,
vsrd.sender_full_name senderFullName,
vm.record_id recordId,
vm.notes_flag notesFlag,
vm.dmi_product product,
vmf.VAERS_LINKED,
vm.VAER_STATUS status,
vm.company_unit_name companyunit,
FIND_WF_ACTIVITY(vm.record_id,JBPM_PROCESS_INST_ID),
vmf.CORRESPONDENCE_FLAG corresFlag,
vmf.READ_UNREAD_CORRESPONDENCE readUnreadCorresp,
vm.vaer_mode vmode,
srcDoc.doc_name,
vsr.seriousnessdecision serious,
vm.reportduedate reportduedate,
vm.MANUALLY_LOCKED,
vm.LOCKED_BY,
vm.LOCKED_REASON,
vm.LOCKED_DATE,
vm.vaer_delete,
vm.vaer_nullify nullify,
vm.archived,
vm.COMPLETION_FLAG,
vm.ASSIGNED_USER_GROUP,
COALESCE(vsrd.TEEATESPECIESDECODE,vsrd.SPECIESDECODE,vsrd.OTHERSPECIES,vsrd.TREATEDSPECIES),
COALESCE(vsrd.ANIMAL_BREEDDECODE,vsrd.TREATED_BREEDDECODE,vsrd.ANIMAL_BREED,vsrd.TREATED_BREED),
vm.APPROVED_VAER,
vm.SUBSTANCE_ADDED,
vm.MULTIPLEBREEDADDED,
msg_q.MDN_DATE,
vm.CASE_SOURCE,
vm.MESSAGENUMB,
vsr.NULLIFICATIONREASON,
vm.CREATED_BY,
vm.ASSESSMENT_SOURCE,
vm.ASSESSMENT_CLASSIFICATION,
vm.DMI_VEDDRA_TERM,
vsr.CASEREGISTRATIONTYPE,
vm.AUTHORIZATIONCOMPANY,
vm.E2B_DMI_PRODUCT brandname,
vm.E2B_SUBSTANCE_ADDED e2bSubstanceAdded,
vm.ACCOUNT account,
ACK.record_id ack_recId ,
vm.SUBMITTED_DELAY
FROM agvet_vae_info vm,
agvet_vae_safetyreport vsr,
agvet_vae_safetyreport_detail vsrd,
AGVET_VAE_SOURCE_DOC srcDoc,
AGVET_VAE_FLAGS vmf,
E2B_MESSAGE_QUEUE msg_q,
E2B_MESSAGE_ACK ACK
WHERE vm.fk_avsr_rec_id = vsr.record_id
AND vsr.fk_avsrd_rec_id = vsrd.record_id
AND srcdoc.record_id(+) = vm.fk_vet_source_doc_rec_id
AND vm.IMPORT_FLAG <> 1
AND (vm.DRAFT_SUBMIT_FLAG = 0
OR vm.DRAFT_SUBMIT_FLAG = 2)
AND vm.VAER_NO = vmf.VAER_NO(+)
AND vm.E2B_MESSAGE_LIST_TYPE<>01
AND vm.MESSAGENUMB = msg_q.MESSAGE_NUMBER(+)
AND vm.MESSAGENUMB = ACK.MESSAGE_NUMBER(+)
AND (vm.assigned_to = 48626
OR vm.assigned_to IS NULL
OR vm.assigned_to = 320538
OR vm.assigned_to = 320529
OR vm.assigned_to = 406699)
AND EXISTS
(SELECT *
FROM jbpm_token jt
WHERE jt.node_ IN ( 135,140,146,137,132,129,127,148,144 )
AND jt.processinstance_ = vm.jbpm_process_inst_id
OR vm.jbpm_process_inst_id IS NULL
)
AND ( fn_access_vet_products(48658,vm.RECORD_ID, vm.CASE_REPORTED_IN)=1)
AND (vm.PRIORITY IN ( 02 )
OR vm.PRIORITY IS NULL)
AND ( upper(vm.CORP_SERIOUS) NOT IN ('1','2') )
AND vm.ARCHIVED = 0
AND vm.vaer_nullify = 0
AND vm.vaer_delete = 0
)
你可以试试这个查询
convert(varchar(50),vm.CORP_SERIOUS) NOT IN('1','2')
值NULL表示未知。
WHERE vm.CORP_SERIOUS IN('1','2')
- “1”为真
- 对于“3”是假的
- 对于 NULL 是 NULL
和
WHERE vm.CORP_SERIOUS NOT IN('1','2')
- 不正确,因此“1”为错误
- 不是 FALSE,因此对于“3”是 TRUE
- 不是 NULL,对于 NULL 又是 NULL
由于 NULL 表示未知,我们不知道该值(我们不知道)是否在给定的集合中。所以答案是"I don't know",无论我们问值是否在列表中或值是否不在列表中。
假设我们不知道约翰的 phone 号码,我给你看一些号码,然后问你约翰的号码是否在其中。你不能说是,你不能说不是,你只能说也许。与 DBMS 相同。它不能告诉你 TRUE 或 FALSE,它只能告诉你 NULL。现在 WHERE 子句的工作方式如下:查询 returns 给定条件为 TRUE 的所有记录。 NULL 不为 TRUE,因此不返回记录。
(即使 NULL 本身在列表中,我们也不知道集合中的未知值是否与记录中的未知值相同。WHERE 子句仍然会导致 NULL。它会使但是 '3' 的区别:WHERE vm.CORP_SERIOUS NOT IN('1','2', null)
也会突然导致 NULL,因为集合中的未知值可能是也可能不是 '3'。)
你可以问:给我所有未知值加上列表中的值。
WHERE vm.CORP_SERIOUS IS NULL OR vm.CORP_SERIOUS NOT IN('1','2')
或者您可以问:
WHERE NVL(vm.CORP_SERIOUS, 'TREAT AS NOT IN THE LIST') NOT IN('1','2')
(嗯,当然字符串 'TREAT AS NOT IN THE LIST' 不能在列表中:-)