实例说明

我们计算用户的年龄,当然只能根据用户的出生年月日信息来计算。这里我们定义:用户出生满1年后,年龄算1岁,不满1年算0岁,以此类推,大于1年不到2年算1岁。

1)根据身份证信息得到用户出生年月日

2)根据出生年月日计算用户当前年龄

身份证规则

18位身份证号码:18位的第二代身份证号码是特征组合码,由十七位数字本体码和一位校验码组成。排列顺序从左至右依次为:六位数字地址码、八位数字出生日期码、三位数字顺序码和一位数字校验码。地址码(前六位数):表示身份证编码对象常住户口所在省份、地市,以及县(市、旗、区)的行政区划代码,按照GB/T2260的规定执行。其中:前1、2位数字表示所在省份的代码;第3、4位数字表示所在地市的代码;第5、6位数字表示:所在县(市、旗、区)的代码。

15位身份证号码: 1、第l一6位数为行政区划代码;是指公民第一次申领居民身份证时的常住户口所在地的行政地区。 2、第7—12位数为出生日期代码; 第7、8位为出生年份(两位数),第9、10位为出生月份,第11、12位代表出生日期。 3、第13—15位数为分配顺序代码;是按人口数统一合理分配以固定顺序给予每个人的顺序号,最末一位数是奇数的分配给男性,偶数分配给女性。

实例代码

package main

import (
	"fmt"
	"strconv"
	"time"
)

// getBirthday 根据身份证获取对应生日
func getBirthday(cardId string) string {
	// 兼容第一代15位身份证号码
	if len(cardId) == 15 {
		// 第一代身份证年份都是19开头的
		return fmt.Sprintf("19%s", cardId[6:12])
	} else {
		return cardId[6:14]
	}
}

// getAgeByBirthday 根据生日日期得到用户年龄
func getAgeByBirthday(birthday string) int {
	year, _ := strconv.Atoi(birthday[0:4])
	month, _ := strconv.Atoi(birthday[4:6])
	day, _ := strconv.Atoi(birthday[6:])

	// 计算当前日期与生日中年月日都差值
	now := time.Now()
	age := now.Year() - year
	moreMonth := int(now.Month()) - month
	moreDay := now.Day() - day

	// 未到生日月份,或者到了月份,但未到生日日期,年龄都要减1岁
	if moreMonth < 0 || (moreMonth == 0 && moreDay < 0) {
		age--
	}
	// 不要出现负值
	if age < 0 {
		age = 0
	}

	return age
}

func main() {
	// 支持15位身份证号码
	cardId1 := "320311770706002"
	birthday1 := getBirthday(cardId1)
	age1 := getAgeByBirthday(birthday1)
	fmt.Println(age1)
	// 当前时间:2023-10-10,输出:46

	// 支持18位身份证号码
	cardId2 := "511702198002221308"
	birthday2 := getBirthday(cardId2)
	age2 := getAgeByBirthday(birthday2)
	fmt.Println(age2)
	// 当前时间:2023-10-10,输出:43
}