当前位置: 首页 > article >正文

oracle 11g写一个判断是否是身份证的函数,函数名称为:FUN_IS_IDENNO

下面是一个用于判断是否是身份证号码的Oracle 11g函数(FUN_IS_IDENNO)。身份证号码通常为18位(或者旧的15位),前17位为数字,第18位为数字或字母X,并且需要符合一定的规则,例如出生日期是否合理,校验位是否正确等。函数来自chatgpt,测试无误

函数逻辑:

  • 1 输入参数:p_idenno,传入的身份证号码。
  • 2 校验逻辑
    1. 判断身份证号的长度是否为18位。
    2. 检查前17位是否为数字。
    3. 验证生日部分是否为有效日期。
    4. 通过身份证的加权因子和校验位规则计算第18位校验码是否正确。
  • 3 返回值
    1. YES 表示身份证号有效。
    2. NO 表示身份证号无效。

在线身份证校验
测试: SELECT FUN_IS_IDENNO('610427197005053353') "是" ,FUN_IS_IDENNO('610424198505184124') "否" FROM DUAL;

CREATE OR REPLACE FUNCTION FUN_IS_IDENNO(p_idenno IN VARCHAR2)
RETURN VARCHAR2
IS
    v_result VARCHAR2(3) := 'NO';
    v_iden_length PLS_INTEGER;
    v_birthday VARCHAR2(8);
    v_year PLS_INTEGER;
    v_month PLS_INTEGER;
    v_day PLS_INTEGER;
    v_check_digit CHAR(1);
    v_check_sum PLS_INTEGER := 0;
    v_weights PLS_INTEGER := 0;
    v_multipliers CONSTANT SYS.ODCINUMBERLIST := SYS.ODCINUMBERLIST(7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2);
    v_check_chars CONSTANT VARCHAR2(11) := '10X98765432';
BEGIN
    -- 获取身份证号码长度
    v_iden_length := LENGTH(p_idenno);
    
    -- 校验身份证长度是否为18位
    IF v_iden_length = 18 THEN
        -- 校验前17位是否为数字
        IF REGEXP_LIKE(SUBSTR(p_idenno, 1, 17), '^\d{17}$') THEN
            -- 校验出生日期是否合理
            v_birthday := SUBSTR(p_idenno, 7, 8);
            v_year := TO_NUMBER(SUBSTR(v_birthday, 1, 4));
            v_month := TO_NUMBER(SUBSTR(v_birthday, 5, 2));
            v_day := TO_NUMBER(SUBSTR(v_birthday, 7, 2));
            
            IF v_year BETWEEN 1900 AND EXTRACT(YEAR FROM SYSDATE) AND v_month BETWEEN 1 AND 12 THEN
                IF (v_month = 2 AND v_day BETWEEN 1 AND 29 AND MOD(v_year, 4) = 0 AND (MOD(v_year, 100) <> 0 OR MOD(v_year, 400) = 0)) OR
                   (v_month = 2 AND v_day BETWEEN 1 AND 28 AND (MOD(v_year, 4) <> 0 OR (MOD(v_year, 100) = 0 AND MOD(v_year, 400) <> 0))) OR
                   (v_month IN (1, 3, 5, 7, 8, 10, 12) AND v_day BETWEEN 1 AND 31) OR
                   (v_month IN (4, 6, 9, 11) AND v_day BETWEEN 1 AND 30) THEN
                   
                   -- 计算校验位
                   FOR i IN 1..17 LOOP
                       v_weights := TO_NUMBER(SUBSTR(p_idenno, i, 1)) * v_multipliers(i);
                       v_check_sum := v_check_sum + v_weights;
                   END LOOP;
                   
                   -- 获取计算出的校验位
                   v_check_digit := SUBSTR(v_check_chars, MOD(v_check_sum, 11) + 1, 1);
                   
                   -- 校验第18位是否正确
                   IF v_check_digit = SUBSTR(p_idenno, 18, 1) THEN
                       v_result := 'YES';
                   END IF;
                END IF;
            END IF;
        END IF;
    END IF;
    
    RETURN v_result;
END FUN_IS_IDENNO;
/


http://www.kler.cn/news/313431.html

相关文章:

  • C++第一次练习
  • WPF 依赖属性改变触发响应事件
  • 反转字符串中的单词--力扣151
  • 影刀RPA实战:网页爬虫之苦瓜书籍数据
  • 前后端分离项目--下载功能
  • 移植Linux:如何制作rootfs?
  • 相机畸变系数$b_1,b_2$与畸变系数aspect ratio和skew的互转
  • css scrollbar-width: none 隐藏默认滚动条
  • WPF DataGrid 列表中,DataGrid.Columns 列根据不同的值显示不同内容
  • MyBatis 源码解析:TypeHandler 设计与自定义实现
  • ★pwn 更改pwn题libc保姆级教程★
  • SpringBoot+Thymeleaf图书管理系统
  • Go语言并发模式详解:深入理解管道与上下文的高级用法
  • 集群聊天服务器项目【C++】项目介绍和环境搭建
  • 【Verilog学习日常】—牛客网刷题—Verilog企业真题—VL77
  • 缓存预热方案详解
  • 论文笔记:交替单模态适应的多模态表征学习
  • WebLogic 后台弱⼝令GetShell
  • WPF入门教学四 WPF控件概述
  • opencv中读取图片、视频以及对其基本操作
  • 关系型数据库,NoSQL和内存数据库三种数据库的比较
  • OpenCV库学习之NMSBoxes函数
  • ubuntu如何进行自动mount硬盘(简易法)
  • Ansible——Playbook基本功能???
  • TortoiseSVN图标不显示的解决
  • 网页交互模拟:模拟用户输入、点击、选择、滚动等交互操作
  • 实习期间git的分枝管理以及最常用的命令
  • PyCharm 安装教程
  • C#+EmguCV合并视频文件
  • Qt Linguist 短语书批量导入翻译.ts导入.qph