@@ -85,6 +85,11 @@ | |||||
<artifactId>commons-lang3</artifactId> | <artifactId>commons-lang3</artifactId> | ||||
<version>3.12.0</version> | <version>3.12.0</version> | ||||
</dependency> | </dependency> | ||||
<dependency> | |||||
<groupId>org.dom4j</groupId> | |||||
<artifactId>dom4j</artifactId> | |||||
<version>RELEASE</version> | |||||
</dependency> | |||||
<!-- https://mvnrepository.com/artifact/org.apache.commons/commons-jexl3 --> | <!-- https://mvnrepository.com/artifact/org.apache.commons/commons-jexl3 --> | ||||
<dependency> | <dependency> | ||||
<groupId>org.apache.commons</groupId> | <groupId>org.apache.commons</groupId> | ||||
@@ -0,0 +1,21 @@ | |||||
package cc.smtweb.framework.core.util; | |||||
public class Consts { | |||||
public static final String BLANK_STRING = " "; | |||||
public static final String NULL_STRING = "-"; | |||||
public static final String TREE_ROOT_ID = "-1"; | |||||
public static final String WORD_LINE_BREAK = "" + (char) 11; | |||||
public static final String CLASS_ROOT_ID = "GB000"; | |||||
public static final String PERSON_TYPE_ROOT_ID = "GP000000"; | |||||
public final static String LEVELCODE_SEPARATOR = "-"; | |||||
public static final String DEF_PWD = "abc@123456"; //初始密码 | |||||
public static final String fileOperator = System.getProperty("file.separator"); | |||||
public static final String TOP_PARTY_ID = "1"; //顶级机构主键 | |||||
public static final String TOP_PARTY_DEFAULT_CODE = "10000"; //顶级单位默认机构编码,初始化后可以到系统中进行修改; | |||||
public final static String DEF_SCHEMA = "sys";//默认的数据库名 | |||||
public final static String FIELD_LAST_TIME = "last_time";//最后更新时间,字段名 | |||||
public final static String FIELD_CREATE_PARTY = "create_party_id";//创建单位,字段名 | |||||
} |
@@ -794,6 +794,15 @@ public class DateUtil { | |||||
if (datetime == null) return null; | if (datetime == null) return null; | ||||
return new java.sql.Date(datetime.getTime()); | return new java.sql.Date(datetime.getTime()); | ||||
} | } | ||||
//获取当前日期所处月,却掉了前置的0. | |||||
public static String nowMonth() { | |||||
String month = nowMonth2(); | |||||
if (month.charAt(0) == '0') { | |||||
return String.valueOf(month.charAt(1)); | |||||
} | |||||
return month; | |||||
} | |||||
/** | /** | ||||
* 将字符串转换成Java.sql.Date,不能转换,这返回null | * 将字符串转换成Java.sql.Date,不能转换,这返回null | ||||
* | * | ||||
@@ -911,6 +920,52 @@ public class DateUtil { | |||||
calendar.setTime(new Date()); | calendar.setTime(new Date()); | ||||
return getSeasonBegin(calendar); | return getSeasonBegin(calendar); | ||||
} | } | ||||
public synchronized static java.sql.Date getAfterDate(Date dt, int days) { | |||||
if (dt == null) return null; | |||||
GregorianCalendar gc = new GregorianCalendar(); | |||||
gc.setTime(dt); | |||||
gc.add(GregorianCalendar.DATE, days); | |||||
return new java.sql.Date(gc.getTimeInMillis()); | |||||
} | |||||
//获取季度结束年月,YYYYMM格式 | |||||
public static String getSeasonEndYm() { | |||||
return getDateYm(getAfterDate(getNextSeasonBegin(), -1)); | |||||
} | |||||
//获取年度开始年月,YYYYMM格式 | |||||
public static String getYearBeginYm() { | |||||
return nowYear() + "01"; | |||||
} | |||||
public static String getYearBeginYm(String ymPeriod) { | |||||
try { | |||||
return ymPeriod.substring(0, 4) + "01"; | |||||
} catch (Exception e) { | |||||
return nowYear() + "01"; | |||||
} | |||||
} | |||||
/** | |||||
* 获取今日日期串,不带分隔符 | |||||
* | |||||
* @return 今日日期字符串 yyyyMMdd; | |||||
*/ | |||||
public static String nowDateString() { | |||||
return simpleDateFormat.get().format(nowTimestamp()); | |||||
} | |||||
//获取年度结束年月,YYYYMM格式 | |||||
public static String getYearEndYm() { | |||||
return nowYear() + "12"; | |||||
} | |||||
public static String getYearEndYm(String ymPeriod) { | |||||
try { | |||||
return ymPeriod.substring(0, 4) + "12"; | |||||
} catch (Exception e) { | |||||
return nowYear() + "12"; | |||||
} | |||||
} | |||||
/** | /** | ||||
* 得到本季度的第一天 | * 得到本季度的第一天 | ||||
* | * | ||||
@@ -979,9 +1034,97 @@ public class DateUtil { | |||||
return getAfterDays(getAfterMonth(getMonthFirstDay(), 1), -1); | return getAfterDays(getAfterMonth(getMonthFirstDay(), 1), -1); | ||||
} | } | ||||
/** | |||||
* 得到本季度最后一天 | |||||
* | |||||
* @return | |||||
*/ | |||||
public static String getSeasonLastDay() { | |||||
String s = toStdDateString(getNextSeasonBegin()); | |||||
return getAfterDays(s, -1); | |||||
} | |||||
//下个季度开始 | |||||
public synchronized static Date getNextSeasonBegin() { | |||||
Calendar calendar = Calendar.getInstance(); | |||||
calendar.setTime(new Date()); | |||||
return getNextSeasonBegin(calendar); | |||||
} | |||||
public synchronized static Date getNextSeasonBegin(Calendar now) { | |||||
int curYear = now.get(Calendar.YEAR); | |||||
int curMonth = now.get(Calendar.MONTH); | |||||
int seasonMonth = m_seasonBeginTable[curMonth] + 3; | |||||
Calendar calendar = Calendar.getInstance(); | |||||
calendar.set(Calendar.YEAR, curYear); | |||||
calendar.set(Calendar.MONTH, seasonMonth); | |||||
calendar.set(Calendar.DAY_OF_MONTH, 1); | |||||
calendar.set(Calendar.HOUR_OF_DAY, 0); | |||||
calendar.set(Calendar.MINUTE, 0); | |||||
calendar.set(Calendar.SECOND, 0); | |||||
calendar.set(Calendar.MILLISECOND, 0); | |||||
calendar.set(Calendar.AM_PM, Calendar.AM); | |||||
return new Timestamp(calendar.getTime().getTime()); | |||||
} | |||||
//获取季度开始年月,YYYYMM格式 | |||||
public static String getSeasonBeginYm() { | |||||
return getDateYm(getSeasonBegin()); | |||||
} | |||||
//获取年月,YYYYMM格式 | |||||
public static String getNowYm() { | |||||
return getDateYm(nowTimestamp()); | |||||
} | |||||
public static String getNextYear(String year, int add) { | |||||
if (PubUtil.isEmptyId(year)) return year; | |||||
int curYear = Integer.parseInt(year) - 1; | |||||
return curYear + ""; | |||||
} | |||||
//获取上一月,YYYYMM格式 | |||||
public static String getPrevYear(String year) { | |||||
return getNextYear(year, -1); | |||||
} | |||||
//获取上一月,YYYYMM格式 | |||||
public static String getPrevYm(String period_id) { | |||||
return getNextYm(period_id, -1); | |||||
} | |||||
//获取下一月,YYYYMM格式 | |||||
public static String getNextYm(String period_id) { | |||||
return getNextYm(period_id, 1); | |||||
} | |||||
//获取年月,YYYYMM格式 | |||||
public static String getPrevYm() { | |||||
return getPrevYm(getNowYm()); | |||||
} | |||||
//获取上一年 YYYY格式 | |||||
public static String getPrevYear() { | |||||
return getPrevYear(nowYear()); | |||||
} | |||||
//获取年月,YYYYMM格式 | |||||
public static String getNextYm() { | |||||
return getNextYm(getNowYm()); | |||||
} | |||||
public static String getNextYm(String period_id, int add) { | |||||
if (PubUtil.isEmptyId(period_id)) return period_id; | |||||
int curYear = Integer.parseInt(period_id.substring(0, 4)); | |||||
int curMonth = Integer.parseInt(period_id.substring(4)) + add; | |||||
if (curMonth > 12) { | |||||
do { | |||||
curYear++; | |||||
curMonth -= 12; | |||||
} while (curMonth > 12); | |||||
} else if (curMonth <= 0) { | |||||
do { | |||||
curYear--; | |||||
curMonth += 12; | |||||
} while (curMonth <= 0); | |||||
} | |||||
return curYear + StringUtil.getRight("00" + curMonth, 2); | |||||
} | |||||
/** | /** | ||||
* 得到当前日期所在周次的星期一 | * 得到当前日期所在周次的星期一 | ||||
* | * | ||||
@@ -0,0 +1,73 @@ | |||||
package cc.smtweb.framework.core.util; | |||||
/** | |||||
* @Author: zhangyulong | |||||
* @Date: 2021/10/13 15:16 | |||||
*/ | |||||
public class EmojiFilter { | |||||
/** | |||||
* 过滤emoji 或者 其他非文字类型的字符 | |||||
* @param source 需要过滤的字符串 | |||||
* @return | |||||
*/ | |||||
public static String filterEmoji(String source) { | |||||
if(PubUtil.isEmpty(source)){ | |||||
return ""; | |||||
} | |||||
if (!containsEmoji(source)) { | |||||
return source; | |||||
} | |||||
StringBuilder buf = null; | |||||
int len = source.length(); | |||||
for (int i = 0; i < len; i++) { | |||||
char codePoint = source.charAt(i); | |||||
if (notisEmojiCharacter(codePoint)) { | |||||
if (buf == null) { | |||||
buf = new StringBuilder(source.length()); | |||||
} | |||||
buf.append(codePoint); | |||||
} | |||||
} | |||||
if (buf == null) { | |||||
return ""; | |||||
} else { | |||||
if (buf.length() == len) { | |||||
buf = null; | |||||
return source; | |||||
} else { | |||||
return buf.toString(); | |||||
} | |||||
} | |||||
} | |||||
/** | |||||
* 检测是否有emoji字符 | |||||
* @param source 需要判断的字符串 | |||||
* @return 一旦含有就抛出 | |||||
*/ | |||||
public static boolean containsEmoji(String source) { | |||||
int len = source.length(); | |||||
for (int i = 0; i < len; i++) { | |||||
char codePoint = source.charAt(i); | |||||
if (!notisEmojiCharacter(codePoint)) { | |||||
return true; | |||||
} | |||||
} | |||||
return false; | |||||
} | |||||
/** | |||||
* 非emoji表情字符判断 | |||||
* @param codePoint | |||||
* @return | |||||
*/ | |||||
public static boolean notisEmojiCharacter(char codePoint) { | |||||
return (codePoint == 0x0) || (codePoint == 0x9) || (codePoint == 0xA) || (codePoint == 0xD) | |||||
|| ((codePoint >= 0x20) && (codePoint <= 0xD7FF)) || ((codePoint >= 0xE000) && (codePoint <= 0xFFFD)) | |||||
|| ((codePoint >= 0x10000) && (codePoint <= 0x10FFFF)); | |||||
} | |||||
} |
@@ -0,0 +1,780 @@ | |||||
package cc.smtweb.framework.core.util; | |||||
import cc.smtweb.framework.core.common.AbstractEnum; | |||||
import cc.smtweb.framework.core.common.IntEnum; | |||||
import cc.smtweb.framework.core.common.StrEnum; | |||||
import org.apache.commons.lang3.StringUtils; | |||||
import java.util.List; | |||||
/** | |||||
* 注意:where参数表示是否已经加入了where关键字 | |||||
* | |||||
* @author : AKzz | |||||
* @version : $Revision:$ | |||||
*/ | |||||
@SuppressWarnings("UnusedDeclaration") | |||||
public abstract class ListSQLParaHelper { | |||||
/** | |||||
* 补充SQL的字符串的==条件 | |||||
* | |||||
* @param where_is_exist 是否已经加入了where关键字 | |||||
*/ | |||||
public static boolean addSql_EQUALE_Expr(boolean where_is_exist, StringBuilder sql, List<Object> args, String db_field_name, int condition_value) { | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
sql.append(db_field_name).append(" = ? \n"); | |||||
args.add(condition_value); | |||||
return true; | |||||
} | |||||
/** | |||||
* 补充SQL的字符串的==条件 | |||||
* | |||||
* @param where_is_exist 是否已经加入了where关键字 | |||||
*/ | |||||
public static boolean addSql_EQUALE_Expr(boolean where_is_exist, StringBuilder sql, List<Object> args, String db_field_name, String condition_value) { | |||||
if (PubUtil.isNotEmptyStr(condition_value)) { | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
where_is_exist = true; | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
sql.append(db_field_name).append(" = ? \n"); | |||||
args.add(condition_value); | |||||
} | |||||
return where_is_exist; | |||||
} | |||||
public static boolean addSql_lesser(boolean where_is_exist, StringBuilder sql, List<Object> args, String db_field_name, String condition_value) { | |||||
if (PubUtil.isNotEmptyStr(condition_value)) { | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
where_is_exist = true; | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
sql.append(db_field_name).append(" <= ? \n"); | |||||
args.add(condition_value); | |||||
} | |||||
return where_is_exist; | |||||
} | |||||
public static boolean addSql_greater(boolean where_is_exist, StringBuilder sql, List<Object> args, String db_field_name, String condition_value) { | |||||
if (PubUtil.isNotEmptyStr(condition_value)) { | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
where_is_exist = true; | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
sql.append(db_field_name).append(" >= ? \n"); | |||||
args.add(condition_value); | |||||
} | |||||
return where_is_exist; | |||||
} | |||||
/** | |||||
* 补充SQL的字符串Like条件(仅后匹配) %s | |||||
* | |||||
* @param where_is_exist 是否已经加入了where关键字 | |||||
*/ | |||||
public static boolean addSql_LIKE_Pre(boolean where_is_exist, StringBuilder sql, List<Object> args, String db_field_name, String condition_value) { | |||||
if (PubUtil.isNotEmptyStr(condition_value)) { | |||||
//mysq _ 是一个占位符需要加\进行处理 | |||||
condition_value = condition_value.replaceAll("_", "\\\\_"); | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
where_is_exist = true; | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
sql.append(db_field_name).append(" LIKE ? \n"); | |||||
args.add(String.format("%%%s", condition_value)); | |||||
} | |||||
return where_is_exist; | |||||
} | |||||
public static boolean addSql_LIKE_Pre(boolean where_is_exist, StringBuilder sql, List<Object> args, String[] db_field_names, String condition_value) { | |||||
if (PubUtil.isNotEmptyStr(condition_value)) { | |||||
//mysq _ 是一个占位符需要加\进行处理 | |||||
condition_value = condition_value.replaceAll("_", "\\\\_"); | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
where_is_exist = true; | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
sql.append("(").append(db_field_names[0]).append(" LIKE ? \n"); | |||||
args.add(String.format("%%%s", condition_value)); | |||||
for (int i = 1; i < db_field_names.length; ++i) { | |||||
sql.append(" or ").append(db_field_names[i]).append(" LIKE ? \n"); | |||||
args.add(String.format("%%%s", condition_value)); | |||||
} | |||||
sql.append(")"); | |||||
} | |||||
return where_is_exist; | |||||
} | |||||
public static boolean addSql_LIKE_EX(boolean where_is_exist, StringBuilder sql, List<Object> args, String condition_value, String... db_field_name) { | |||||
if (db_field_name == null || db_field_name.length == 0) return where_is_exist; | |||||
if (PubUtil.isNotEmptyStr(condition_value)) { | |||||
//mysq _ 是一个占位符需要加\进行处理 | |||||
condition_value = condition_value.replaceAll("_", "\\\\_"); | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
where_is_exist = true; | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
if (db_field_name.length == 1) { | |||||
sql.append(db_field_name[0]).append(" LIKE ? \n"); | |||||
args.add(String.format("%%%s%%", condition_value)); | |||||
return where_is_exist; | |||||
} | |||||
sql.append(" ("); | |||||
for (String db_filed : db_field_name) { | |||||
sql.append(" ").append(db_filed).append(" LIKE ? \nOR"); | |||||
args.add(String.format("%%%s%%", condition_value)); | |||||
} | |||||
sql.delete(sql.length() - 2, sql.length()); | |||||
sql.append(")\n"); | |||||
} | |||||
return where_is_exist; | |||||
} | |||||
/** | |||||
* 补充SQL的字符串Like条件(仅后匹配) s% | |||||
* | |||||
* @param where_is_exist 是否已经加入了where关键字 | |||||
*/ | |||||
public static boolean addSql_LIKE_Expr(boolean where_is_exist, StringBuilder sql, List<Object> args, String db_field_name, String condition_value) { | |||||
if (PubUtil.isNotEmptyStr(condition_value)) { | |||||
//mysq _ 是一个占位符需要加\进行处理 | |||||
condition_value = condition_value.replaceAll("_", "\\\\_"); | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
where_is_exist = true; | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
sql.append(db_field_name).append(" LIKE ? \n"); | |||||
args.add(String.format("%s%%", condition_value)); | |||||
} | |||||
return where_is_exist; | |||||
} | |||||
public static boolean addSql_LIKE_Expr(boolean where_is_exist, StringBuilder sql, List<Object> args, String[] db_field_names, String condition_value) { | |||||
if (PubUtil.isNotEmptyStr(condition_value)) { | |||||
//mysq _ 是一个占位符需要加\进行处理 | |||||
condition_value = condition_value.replaceAll("_", "\\\\_"); | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
where_is_exist = true; | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
sql.append("(").append(db_field_names[0]).append(" LIKE ? \n"); | |||||
args.add(String.format("%s%%", condition_value)); | |||||
for (int i = 1; i < db_field_names.length; ++i) { | |||||
sql.append(" or ").append(db_field_names[i]).append(" LIKE ? \n"); | |||||
args.add(String.format("%s%%", condition_value)); | |||||
} | |||||
sql.append(")"); | |||||
} | |||||
return where_is_exist; | |||||
} | |||||
/** | |||||
* 补充SQL的字符串Like条件(全模糊) %s% | |||||
* | |||||
* @param where_is_exist 是否已经加入了where关键字 | |||||
*/ | |||||
public static boolean addSql_LIKE(boolean where_is_exist, StringBuilder sql, List<Object> args, String db_field_name, String condition_value) { | |||||
if (PubUtil.isNotEmptyStr(condition_value)) { | |||||
//mysq _ 是一个占位符需要加\进行处理 | |||||
condition_value = condition_value.replaceAll("_", "\\\\_"); | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
where_is_exist = true; | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
sql.append(db_field_name).append(" LIKE ? \n"); | |||||
args.add(String.format("%%%s%%", condition_value)); | |||||
} | |||||
return where_is_exist; | |||||
} | |||||
public static boolean addSql_LIKE(boolean where_is_exist, StringBuilder sql, List<Object> args, String[] db_field_names, String condition_value) { | |||||
if (PubUtil.isNotEmptyStr(condition_value)) { | |||||
//mysq _ 是一个占位符需要加\进行处理 | |||||
condition_value = condition_value.replaceAll("_", "\\\\_"); | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
where_is_exist = true; | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
sql.append("(").append(db_field_names[0]).append(" LIKE ? "); | |||||
args.add(String.format("%%%s%%", condition_value)); | |||||
for (int i = 1; i < db_field_names.length; ++i) { | |||||
sql.append(" OR ").append(db_field_names[i]).append(" LIKE ? "); | |||||
args.add(String.format("%%%s%%", condition_value)); | |||||
} | |||||
sql.append(")"); | |||||
} | |||||
return where_is_exist; | |||||
} | |||||
/** | |||||
* 补充SQL字符串的IN条件 | |||||
* | |||||
* @param where_is_exist 是否已经加入了where关键字 | |||||
*/ | |||||
public static boolean addSql_IN_Expr(boolean where_is_exist, StringBuilder sql, String db_field_name, Object... expr) { | |||||
if (expr != null && expr.length > 0) { | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
where_is_exist = true; | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
sql.append(db_field_name).append(" IN (").append(StringUtils.join(expr, ',')).append(")\n"); | |||||
} | |||||
return where_is_exist; | |||||
} | |||||
/** | |||||
* 补充SQL字符串的not IN条件 | |||||
* | |||||
* @param where_is_exist 是否已经加入了where关键字 | |||||
*/ | |||||
public static boolean addSql_NOTIN_Expr(boolean where_is_exist, StringBuilder sql, String db_field_name, Object... expr) { | |||||
if (expr != null && expr.length > 0) { | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
where_is_exist = true; | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
sql.append(db_field_name).append(" NOT IN (").append(StringUtils.join(expr, ',')).append(")\n"); | |||||
} | |||||
return where_is_exist; | |||||
} | |||||
/** | |||||
* 增加字符串字段条件,可能多选 | |||||
* | |||||
* @param field 查询的字段名 | |||||
* @param value 值,包含','为多选 | |||||
* @param sql sql | |||||
* @param paras 参数 | |||||
*/ | |||||
public static void addStrConMulti(String field, String value, StringBuilder sql, List<Object> paras) { | |||||
if (PubUtil.isEmpty(value)) | |||||
return; | |||||
if (value.contains(",")) {//多选 | |||||
sql.append(" and ").append(field).append(" in ('").append(value.replaceAll(",", "','")).append("')"); | |||||
} else if (!Consts.NULL_STRING.equals(value)) {//单 | |||||
sql.append(" and ").append(field).append("=?"); | |||||
paras.add(value); | |||||
} | |||||
} | |||||
/** | |||||
* 增加字符串字段条件,不判断多选 | |||||
* | |||||
* @param field 查询的字段名 | |||||
* @param value 值 | |||||
* @param paras 参数 | |||||
*/ | |||||
public static void addStrConSingle(String field, String value, StringBuilder sb, List<Object> paras) { | |||||
addStrConSingle(field, "=", value, sb, paras); | |||||
} | |||||
/** | |||||
* 增加字符串字段条件,不判断多选 | |||||
* | |||||
* @param field 查询的字段名 | |||||
* @param opt 逻辑运算符 | |||||
* @param value 值 | |||||
* @param paras 参数 | |||||
*/ | |||||
public static void addStrConSingle(String field, String opt, String value, StringBuilder sb, List<Object> paras) { | |||||
if (PubUtil.isNotEmpty(value) && !Consts.NULL_STRING.equals(value)) {//单 | |||||
sb.append(" and ").append(field).append(" ").append(opt).append(" ? \n"); | |||||
paras.add(value); | |||||
} | |||||
} | |||||
/** | |||||
* 增加字符串字段条件,包含 | |||||
* | |||||
* @param field 查询的字段名 | |||||
* @param value 值 | |||||
* @param paras 参数 | |||||
*/ | |||||
public static void addStrConSingleLike(String field, String value, StringBuilder sb, List<Object> paras) { | |||||
if (PubUtil.isNotEmpty(value) && !Consts.NULL_STRING.equals(value)) {//单 | |||||
sb.append(" and ").append(field).append(" like ? \n"); | |||||
paras.add("%" + value + "%"); | |||||
} | |||||
} | |||||
/** | |||||
* 增加字符串字段条件并且不区分大小写,包含 | |||||
* | |||||
* @param field 查询的字段名 | |||||
* @param value 值 | |||||
* @param paras 参数 | |||||
*/ | |||||
public static void addStrConSingleLikeIgnoreCase(String field, String value, StringBuilder sb, List<Object> paras) { | |||||
if (PubUtil.isNotEmpty(value) && !Consts.NULL_STRING.equals(value)) { | |||||
String valueLower = value.toLowerCase(); | |||||
sb.append(" and ").append("lower(").append(field).append(")").append(" like ? \n"); | |||||
paras.add("%" + valueLower + "%"); | |||||
} | |||||
} | |||||
/** | |||||
* 增加数字字段条件,可能多选 | |||||
* | |||||
* @param field 查询的字段名 | |||||
* @param value 值,包含','为多选 | |||||
* @param paras 参数 | |||||
*/ | |||||
public static void addNumberConMulti(String field, String value, StringBuilder sb, List<Object> paras) { | |||||
if (PubUtil.isEmptyId(value)) | |||||
return; | |||||
if (value.contains(",")) {//多选 | |||||
sb.append(" and ").append(field).append(" in (").append(value).append(") \n"); | |||||
} else if (!Consts.NULL_STRING.equals(value)) {//单 | |||||
sb.append(" and ").append(field).append("=? \n"); | |||||
paras.add(value); | |||||
} | |||||
} | |||||
/** | |||||
* 增加数字字段条件,单选 | |||||
* | |||||
* @param field 查询的字段名 | |||||
* @param value 值 | |||||
* @param paras 参数 | |||||
*/ | |||||
public static void addNumConSingle(String field, Number value, StringBuilder sb, List<Object> paras) { | |||||
addNumConSingle(field, "=", value, sb, paras); | |||||
} | |||||
/** | |||||
* 增加数字字段条件,单选 | |||||
* | |||||
* @param field 查询的字段名 | |||||
* @param opt 运算符 | |||||
* @param value 值 | |||||
* @param paras 参数 | |||||
*/ | |||||
public static void addNumConSingle(String field, String opt, Number value, StringBuilder sb, List<Object> paras) { | |||||
sb.append(" and ").append(field).append(opt).append("? \n"); | |||||
paras.add(value); | |||||
} | |||||
/** | |||||
* 增加日期字段条件,可能多选 | |||||
* | |||||
* @param field 查询的字段名 | |||||
* @param value 值 | |||||
* @param paras 参数 | |||||
*/ | |||||
@Deprecated | |||||
public static void addDateCon(String field, String value, StringBuilder sb, List<Object> paras) { | |||||
if (PubUtil.isEmpty(value)) | |||||
return; | |||||
String[] st = value.split(","); | |||||
if (st.length == 0 || Consts.NULL_STRING.equals(st[0])) {//无 | |||||
return; | |||||
} | |||||
String s = PubUtil.getCurDateStr(); | |||||
if (st.length > 0) { | |||||
switch (st[0]) { | |||||
case "D": //当天 考虑日期时间的情况 | |||||
sb.append(" and ").append(field).append(">='").append(s).append("' and ").append(field).append("<'").append(DateUtil.getAfterDays(s, 1)).append("' \n"); | |||||
break; | |||||
case "W": //本周 | |||||
s = DateUtil.toStdDateString(DateUtil.getWeekStart()); | |||||
sb.append(" and ").append(field).append(">='").append(s).append("' and ").append(field).append("<'").append(DateUtil.getAfterDays(s, 8)).append("' \n"); | |||||
break; | |||||
case "M": //本月 | |||||
sb.append(" and ").append(field).append(">='").append(DateUtil.getMonthStart()).append("' and ").append(field).append("<='").append(DateUtil.getMonthEnd()).append(" 23:59:59' \n"); | |||||
break; | |||||
case "Q": //本季度 | |||||
sb.append(" and ").append(field).append(">='").append(DateUtil.getSeasonFirstDay()).append("' and ").append(field).append("<='").append(DateUtil.getSeasonLastDay()).append(" 23:59:59' \n"); | |||||
break; | |||||
case "Y": //本年 | |||||
sb.append(" and ").append(field).append(">='").append(DateUtil.getYearFirstDay()).append("' and ").append(field).append("<='").append(DateUtil.getYearLastDay()).append(" 23:59:59' \n"); | |||||
break; | |||||
default: //自定义 | |||||
String df, de; | |||||
if (st.length > 1) | |||||
df = st[1]; | |||||
else | |||||
df = ""; | |||||
if (st.length > 2) | |||||
de = st[2]; | |||||
else | |||||
de = ""; | |||||
if (PubUtil.isEmpty(df) && PubUtil.isEmpty(de)) | |||||
return; | |||||
if (PubUtil.isEmpty(df)) { | |||||
sb.append(" and ").append(field).append("<=?"); | |||||
paras.add(de); | |||||
} else if (PubUtil.isEmpty(de)) { | |||||
sb.append(" and ").append(field).append(">=?"); | |||||
paras.add(df); | |||||
} else { | |||||
sb.append(" and ").append(field).append(">=? and ").append(field).append("<=? \n"); | |||||
paras.add(df); | |||||
paras.add(de); | |||||
} | |||||
break; | |||||
} | |||||
} | |||||
} | |||||
/** | |||||
* 增加日期字段条件,可能多选(huangxl:日期格式YYYYMMDD) | |||||
* | |||||
* @param field 查询的字段名 | |||||
* @param value 值 | |||||
* @param paras 参数 | |||||
*/ | |||||
public static void addDateConEx(String field, String value, StringBuilder sb, List<Object> paras) { | |||||
if (PubUtil.isEmpty(value)) | |||||
return; | |||||
String[] st = value.split(","); | |||||
if (st.length == 0 || Consts.NULL_STRING.equals(st[0])) {//无 | |||||
return; | |||||
} | |||||
String s = PubUtil.getCurDateStr(); | |||||
if (st.length > 0) { | |||||
switch (st[0]) { | |||||
case "D": //当天 | |||||
sb.append(" and ").append(field).append("=").append(PubUtil.getDateLong(s)).append(" \n"); | |||||
break; | |||||
case "W": //本周 | |||||
s = DateUtil.toStdDateString(DateUtil.getWeekStart()); | |||||
sb.append(" and ").append(field).append(" between ").append(PubUtil.getDateLong(s)).append(" and ").append(PubUtil.getDateLong(DateUtil.getAfterDays(s, 7))).append(" \n"); | |||||
break; | |||||
case "M": //本月 | |||||
sb.append(" and ").append(field).append(" between ").append(PubUtil.getDateLong(DateUtil.getMonthStart())).append(" and ").append(PubUtil.getDateLong(DateUtil.getMonthEnd())).append(" \n"); | |||||
break; | |||||
case "Q": //本季度 | |||||
sb.append(" and ").append(field).append(" between ").append(PubUtil.getDateLong(DateUtil.getSeasonFirstDay())).append(" and ").append(PubUtil.getDateLong(DateUtil.getSeasonLastDay())).append(" \n"); | |||||
break; | |||||
case "Y": //本年 | |||||
sb.append(" and ").append(field).append(" between ").append(PubUtil.getDateLong(DateUtil.getYearFirstDay())).append(" and ").append(PubUtil.getDateLong(DateUtil.getYearLastDay())).append(" \n"); | |||||
break; | |||||
default: //自定义 | |||||
String df, de; | |||||
if (st.length > 1) | |||||
df = st[1]; | |||||
else | |||||
df = ""; | |||||
if (st.length > 2) | |||||
de = st[2]; | |||||
else | |||||
de = ""; | |||||
if (PubUtil.isEmpty(df) && PubUtil.isEmpty(de)) | |||||
return; | |||||
if (PubUtil.isEmpty(df)) { | |||||
sb.append(" and ").append(field).append("<=?"); | |||||
paras.add(PubUtil.getDateLong(de)); | |||||
} else if (PubUtil.isEmpty(de)) { | |||||
sb.append(" and ").append(field).append(">=?"); | |||||
paras.add(PubUtil.getDateLong(df)); | |||||
} else { | |||||
sb.append(" and ").append(field).append(" between ? and ? \n"); | |||||
paras.add(PubUtil.getDateLong(df)); | |||||
paras.add(PubUtil.getDateLong(de)); | |||||
} | |||||
break; | |||||
} | |||||
} | |||||
} | |||||
/** | |||||
* 增加期间查询日期字段条件,可能多选(huangxl:日期格式YYYYMMDD) | |||||
* | |||||
* @param field 查询的字段名 | |||||
* @param value 值 | |||||
* @param paras 参数 | |||||
*/ | |||||
public static void addPeriodDateConEx(String field, String value, StringBuilder sb, List<Object> paras) { | |||||
if (PubUtil.isEmpty(value)) | |||||
return; | |||||
String[] st = value.split(","); | |||||
if (st.length == 0 || Consts.NULL_STRING.equals(st[0])) {//无 | |||||
return; | |||||
} | |||||
String df, de; | |||||
if (st.length > 1) | |||||
df = st[1]; | |||||
else | |||||
df = ""; | |||||
if (st.length > 2) | |||||
de = st[2]; | |||||
else | |||||
de = ""; | |||||
sb.append(" and ").append(field).append(" between ? and ? \n"); | |||||
paras.add(df + "01"); | |||||
paras.add(de + "31"); | |||||
} | |||||
/** | |||||
* 增加日期时间字段条件 | |||||
* | |||||
* @param field 查询的字段名 | |||||
* @param value 值 | |||||
* @param paras 参数 | |||||
*/ | |||||
public static void addDateTimeConEx(String field, String value, StringBuilder sb, List<Object> paras) { | |||||
if (PubUtil.isEmpty(value)) | |||||
return; | |||||
String[] st = value.split(","); | |||||
if (st.length == 0 || Consts.NULL_STRING.equals(st[0])) {//无 | |||||
return; | |||||
} | |||||
String s = PubUtil.getCurDateStr(); | |||||
if (st.length > 0) { | |||||
switch (st[0]) { | |||||
case "D": //当天 | |||||
sb.append(" and ").append(field).append(" between ").append(PubUtil.getDateTimeLong(s)).append(" and ").append(PubUtil.getEndDateTimeLong(s)).append(" \n"); | |||||
break; | |||||
case "W": //本周 | |||||
s = DateUtil.toStdDateString(DateUtil.getWeekStart()); | |||||
sb.append(" and ").append(field).append(" between ").append(PubUtil.getDateTimeLong(s)).append(" and ").append(PubUtil.getEndDateTimeLong(DateUtil.getAfterDays(s, 6))).append(" \n"); | |||||
break; | |||||
case "M": //本月 | |||||
sb.append(" and ").append(field).append(" between ").append(PubUtil.getDateTimeLong(DateUtil.getMonthStart())).append(" and ").append(PubUtil.getEndDateTimeLong(DateUtil.getMonthEnd())).append(" \n"); | |||||
break; | |||||
case "Q": //本季度 | |||||
sb.append(" and ").append(field).append(" between ").append(PubUtil.getDateTimeLong(DateUtil.getSeasonFirstDay())).append(" and ").append(PubUtil.getEndDateTimeLong(DateUtil.getSeasonLastDay())).append(" \n"); | |||||
break; | |||||
case "Y": //本年 | |||||
sb.append(" and ").append(field).append(" between ").append(PubUtil.getDateTimeLong(DateUtil.getYearFirstDay())).append(" and ").append(PubUtil.getEndDateTimeLong(DateUtil.getYearLastDay())).append(" \n"); | |||||
break; | |||||
default: //自定义 | |||||
String df, de; | |||||
if (st.length > 1) | |||||
df = st[1]; | |||||
else | |||||
df = ""; | |||||
if (st.length > 2) | |||||
de = st[2]; | |||||
else | |||||
de = ""; | |||||
if (PubUtil.isEmpty(df) && PubUtil.isEmpty(de)) | |||||
return; | |||||
if (PubUtil.isEmpty(df)) { | |||||
sb.append(" and ").append(field).append("<=?"); | |||||
paras.add(PubUtil.getEndDateTimeLong(de)); | |||||
} else if (PubUtil.isEmpty(de)) { | |||||
sb.append(" and ").append(field).append(">=?"); | |||||
paras.add(PubUtil.getDateTimeLong(df)); | |||||
} else { | |||||
sb.append(" and ").append(field).append(" between ? and ? \n"); | |||||
paras.add(PubUtil.getDateTimeLong(df)); | |||||
paras.add(PubUtil.getEndDateTimeLong(de)); | |||||
} | |||||
break; | |||||
} | |||||
} | |||||
} | |||||
/** | |||||
* 枚举状态字段,in方式 | |||||
* | |||||
* @param where_is_exist sql是否已包括where | |||||
* @param field sql字段名 | |||||
* @param value 前端传回来的查询值,格式:1,1,1,1 | |||||
* @param intEnum 枚举类型 | |||||
* @param sql 待构建的sql | |||||
*/ | |||||
public static void addIntEnumCon(boolean where_is_exist, String field, String value, IntEnum intEnum, StringBuilder sql) { | |||||
if (PubUtil.isNotEmpty(value) && value.contains("1") && value.contains("0")) { | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
where_is_exist = true; | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
String s = ""; | |||||
String[] ss = value.split(","); | |||||
int i = 0; | |||||
for (AbstractEnum.IntEnumBean b : intEnum.values()) { | |||||
if (ss.length > i && "1".equals(ss[i])) s += "," + b.value; | |||||
i++; | |||||
} | |||||
sql.append(field + " in (" + s.substring(1) + ")"); | |||||
} | |||||
} | |||||
/** | |||||
* 枚举状态字段,in方式 | |||||
* | |||||
* @param where_is_exist sql是否已包括where | |||||
* @param field sql字段名 | |||||
* @param value 前端传回来的查询值,格式:1,1,1,1 | |||||
* @param intEnum 枚举类型 | |||||
* @param sql 待构建的sql | |||||
*/ | |||||
public static void addStrEnumCon(boolean where_is_exist, String field, String value, StrEnum intEnum, StringBuilder sql) { | |||||
if (PubUtil.isNotEmpty(value) && value.contains("1") && value.contains("0")) { | |||||
if (!where_is_exist) { | |||||
sql.append(" WHERE "); | |||||
where_is_exist = true; | |||||
} else { | |||||
sql.append(" AND "); | |||||
} | |||||
String s = ""; | |||||
String[] ss = value.split(","); | |||||
int i = 0; | |||||
for (AbstractEnum.StrEnumBean b : intEnum.values()) { | |||||
if (ss.length > i && "1".equals(ss[i])) s += ",'" + b.value + "'"; | |||||
i++; | |||||
} | |||||
sql.append(field + " in (" + s.substring(1) + ")"); | |||||
} | |||||
} | |||||
public static void addTreeStateCon(String curPrefix, String value, String tableName, StringBuilder sb, List<Object> paras) { | |||||
if (PubUtil.isNotEmpty(value) && !Consts.NULL_STRING.equals(value) && !value.contains(",")) { | |||||
int v = PubUtil.getIntIgnoreErr(value); | |||||
if (v == 0) {//查启用 自己启用,且父亲未停用 | |||||
sb.append(" and ").append(curPrefix).append(".f_status=0 and not exists(select 1 from ").append(tableName).append(" p__ where p__.f_status=1 and ").append(curPrefix).append(".f_level_code like p__.f_level_code || '-%')"); | |||||
} else {//查停用 自己停用 或父亲被停用 | |||||
sb.append(" and (").append(curPrefix).append(".f_status=1 or exists(select 1 from ").append(tableName).append(" p__ where p__.f_status=1 and ").append(curPrefix).append(".f_level_code like p__.f_level_code || '-%'))"); | |||||
} | |||||
} | |||||
} | |||||
/** | |||||
* 增加年月字段条件 | |||||
* | |||||
* @param field 查询的字段名 | |||||
* @param value 值 | |||||
* @param paras 参数 | |||||
*/ | |||||
public static void addYmCon(String field, String value, StringBuilder sb, List<Object> paras) { | |||||
addYmConEx(field, field, value, sb, paras); | |||||
} | |||||
public static void addYmConEx(String field_begin, String field_end, String value, StringBuilder sb, List<Object> paras) { | |||||
if (PubUtil.isEmpty(value)) | |||||
return; | |||||
String[] st = value.split(","); | |||||
if (st.length == 0 || Consts.NULL_STRING.equals(st[0])) {//无 | |||||
return; | |||||
} | |||||
String s = PubUtil.getCurDateStr(); | |||||
if (st.length > 1) { | |||||
switch (st[0]) { | |||||
case "M": //本月 | |||||
String nowYm = DateUtil.getNowYm(); | |||||
sb.append(" and ").append(field_end).append(">='").append(DateUtil.getNowYm()).append("' and ").append(field_begin).append("<='").append(nowYm).append("'"); | |||||
break; | |||||
case "Q": //本季度 | |||||
sb.append(" and ").append(field_end).append(">='").append(DateUtil.getSeasonBeginYm()).append("' and ").append(field_begin).append("<='").append(DateUtil.getSeasonEndYm()).append("'"); | |||||
break; | |||||
case "Y": //本年 | |||||
sb.append(" and ").append(field_end).append(">='").append(DateUtil.getYearBeginYm()).append("' and ").append(field_begin).append("<='").append(DateUtil.getYearEndYm()).append("'"); | |||||
break; | |||||
default: //自定义 | |||||
String df, de; | |||||
if (st.length > 1) | |||||
df = st[1]; | |||||
else | |||||
df = ""; | |||||
if (st.length > 2) | |||||
de = st[2]; | |||||
else | |||||
de = ""; | |||||
if (PubUtil.isEmpty(df) && PubUtil.isEmpty(de)) | |||||
return; | |||||
if (PubUtil.isEmpty(df)) { | |||||
sb.append(" and ").append(field_begin).append("<=?"); | |||||
paras.add(de); | |||||
} else if (PubUtil.isEmpty(de)) { | |||||
sb.append(" and ").append(field_end).append(">=?"); | |||||
paras.add(df); | |||||
} else { | |||||
sb.append(" and ").append(field_end).append(">=? and ").append(field_begin).append("<=?"); | |||||
paras.add(df); | |||||
paras.add(de); | |||||
} | |||||
break; | |||||
} | |||||
} else if (st.length == 1) { | |||||
sb.append(" and ").append(field_end).append(">='").append(value).append("' and ").append(field_begin).append("<='").append(value).append("'"); | |||||
} | |||||
} | |||||
//构建年月范围的sql | |||||
public static String getYmConSql(String field, String value) { | |||||
return getYmConSqlEx(field, field, value); | |||||
} | |||||
public static String getYmConSqlEx(String field_begin, String field_end, String value) { | |||||
if (PubUtil.isEmpty(value)) return ""; | |||||
String[] st = value.split(","); | |||||
if (st.length == 0 || Consts.NULL_STRING.equals(st[0])) return ""; | |||||
String s = PubUtil.getCurDateStr(); | |||||
StringBuilder sb = new StringBuilder(128); | |||||
switch (st[0]) { | |||||
case "M": //本月 | |||||
String nowYm = DateUtil.getNowYm(); | |||||
sb.append(" and ").append(field_end).append(">='").append(DateUtil.getNowYm()).append("' and ").append(field_begin).append("<='").append(nowYm).append("'"); | |||||
break; | |||||
case "Q": //本季度 | |||||
sb.append(" and ").append(field_end).append(">='").append(DateUtil.getSeasonBeginYm()).append("' and ").append(field_begin).append("<='").append(DateUtil.getSeasonEndYm()).append("'"); | |||||
break; | |||||
case "Y": //本年 | |||||
sb.append(" and ").append(field_end).append(">='").append(DateUtil.getYearBeginYm()).append("' and ").append(field_begin).append("<='").append(DateUtil.getYearEndYm()).append("'"); | |||||
break; | |||||
default: //自定义 | |||||
String df, de; | |||||
if (st.length > 1) | |||||
df = st[1]; | |||||
else | |||||
df = ""; | |||||
if (st.length > 2) | |||||
de = st[2]; | |||||
else | |||||
de = ""; | |||||
if (PubUtil.isEmpty(df) && PubUtil.isEmpty(de)) | |||||
return ""; | |||||
if (PubUtil.isEmpty(df)) { | |||||
sb.append(" and ").append(field_begin).append("<='").append(de).append("'"); | |||||
} else if (PubUtil.isEmpty(de)) { | |||||
sb.append(" and ").append(field_end).append(">='").append(df).append("'"); | |||||
} else { | |||||
sb.append(" and ").append(field_end).append(">='").append(df).append("' and ").append(field_begin).append("<='").append(de).append("'"); | |||||
} | |||||
break; | |||||
} | |||||
return sb.substring(5); | |||||
} | |||||
} |
@@ -0,0 +1,463 @@ | |||||
package cc.smtweb.framework.core.util; | |||||
import java.math.BigDecimal; | |||||
import java.math.RoundingMode; | |||||
import java.text.DecimalFormat; | |||||
/** | |||||
* Created with IntelliJ IDEA. | |||||
* User: AKhh | |||||
* Date: 12-12-25 下午1:02 | |||||
* To change this template use File | Settings | File Templates. | |||||
*/ | |||||
public class MathUtil { | |||||
//整数 | |||||
private static DecimalFormat dfLng = new DecimalFormat("##############0"); | |||||
private static DecimalFormat dfLong = new DecimalFormat("###,###,###,###,##0"); | |||||
//一位小数 | |||||
private static DecimalFormat df1 = new DecimalFormat("##############0.0"); | |||||
private static DecimalFormat df1Format = new DecimalFormat("###,###,###,###,##0.0"); | |||||
//两位小数 | |||||
private static DecimalFormat df2 = new DecimalFormat("##############0.00"); | |||||
private static DecimalFormat df2Format = new DecimalFormat("###,###,###,###,##0.00"); | |||||
//四位小数 | |||||
private static DecimalFormat df4 = new DecimalFormat("###,###,###,###,##0.0000"); | |||||
//六位小数 | |||||
private static DecimalFormat df6Number = new DecimalFormat("#######################0.000000"); | |||||
private static DecimalFormat df6NumberF = new DecimalFormat("#,###,###,###,###,###,##0.000000"); | |||||
public final static DecimalFormat stdAmountFormat = new DecimalFormat("###,###,###,###,##0.00"); | |||||
public final static DecimalFormat stdNumberFormat = new DecimalFormat("#0.00"); | |||||
public final static String DEF_NUM_TEN_THOUSAND = "10000";//万 | |||||
public static final double MAX_VALUE = 9999999999999.99D; | |||||
public static final double MIN_VALUE = -9999999999999.99D; | |||||
private final static BigDecimal ONE_BIG = new BigDecimal(1.00D); | |||||
private static final String UNIT = "万仟佰拾亿仟佰拾万仟佰拾元角分"; | |||||
private static final String DIGIT = "零壹贰叁肆伍陆柒捌玖"; | |||||
/** | |||||
* 4舍5入double,2位小数 | |||||
*/ | |||||
public static double roundDouble(double src) { | |||||
return roundDouble(src, 2); | |||||
} | |||||
/** | |||||
* 4舍5入double,N 位小数 | |||||
* @param src | |||||
* @param scale 小数位数 | |||||
* @return | |||||
*/ | |||||
public static double roundDouble(Object src, int scale) { | |||||
if (src == null) return 0.0; | |||||
String v = src.toString(); | |||||
if (PubUtil.isEmpty(v)) return 0.0; | |||||
if (scale < 0) scale = 2; | |||||
BigDecimal src_b = new BigDecimal(v); | |||||
BigDecimal src_v = src_b.divide(ONE_BIG, scale + 2, BigDecimal.ROUND_HALF_UP);// 4舍5入 | |||||
src_v = src_v.divide(ONE_BIG, scale, BigDecimal.ROUND_HALF_UP);// 4舍5入 | |||||
return src_v.doubleValue(); | |||||
} | |||||
/** | |||||
* 舍位处理,原生floor有坑,部分浮点数记录为.99999999999形式,导致floor结果错误 | |||||
* @param d | |||||
* @return | |||||
*/ | |||||
public static double floor(double d) { | |||||
return Math.floor(roundDouble(d, 2)); | |||||
} | |||||
/** | |||||
* 比较两Double是否相等,将会吧他们专程BigDecimal进行比较; | |||||
* | |||||
* @param src double1 | |||||
* @param tag double2 | |||||
* @return src > tag 返回1, src < tag 返回-1, 否则返回0 | |||||
*/ | |||||
public static int compare(double src, double tag) { | |||||
BigDecimal src_b = new BigDecimal(src); | |||||
BigDecimal src_v = src_b.divide(ONE_BIG, 2, BigDecimal.ROUND_HALF_UP);// 4舍5入 | |||||
BigDecimal tag_b = new BigDecimal(tag); | |||||
BigDecimal tag_v = tag_b.divide(ONE_BIG, 2, BigDecimal.ROUND_HALF_UP);// 4舍5入 | |||||
return src_v.compareTo(tag_v); | |||||
} | |||||
/** | |||||
* 自动过滤金额中的逗号转换为double,如果出错,则返回0 | |||||
* | |||||
* @param s 源串,可能为带逗号的金额串; | |||||
* @return double | |||||
*/ | |||||
public static Double toDouble(String s) { | |||||
return todouble(s); | |||||
} | |||||
/** | |||||
* 自动过滤金额中的逗号转换为double,如果出错,则返回0 | |||||
* | |||||
* @param s 源串,可能为带逗号的金额串; | |||||
* @return double | |||||
*/ | |||||
public static double todouble(String s) { | |||||
try { | |||||
return Double.parseDouble(s.replaceAll(",", "")); | |||||
} catch (Exception e) { | |||||
return 0.00; | |||||
} | |||||
} | |||||
/** | |||||
* 获取double,主要过滤d为null的情况; | |||||
* | |||||
* @param d Double对象; | |||||
* @return double | |||||
*/ | |||||
public static double todouble(Double d) { | |||||
if (d == null) return 0.0d; | |||||
return d.doubleValue(); | |||||
} | |||||
/** | |||||
* 自动过滤金额中的逗号转换为float,如果出错,则返回0 | |||||
* | |||||
* @param s 源串,可能为带逗号的金额串; | |||||
* @return Float | |||||
*/ | |||||
public static Float toFloat(String s) { | |||||
return tofloat(s); | |||||
} | |||||
/** | |||||
* 自动过滤金额中的逗号转换为float,如果出错,则返回0 | |||||
* | |||||
* @param s 源串,可能为带逗号的金额串; | |||||
* @return Float | |||||
*/ | |||||
public static float tofloat(String s) { | |||||
try { | |||||
return Float.parseFloat(s.replaceAll(",", "")); | |||||
} catch (Exception e) { | |||||
return 0.0f; | |||||
} | |||||
} | |||||
public static long tolong(String src, long defaultvalue) { | |||||
try { | |||||
return Long.parseLong(src); | |||||
} catch (Exception e) { | |||||
return defaultvalue; | |||||
} | |||||
} | |||||
public static int toint(String src, int defaultvalue) { | |||||
try { | |||||
return Integer.parseInt(src); | |||||
} catch (Exception e) { | |||||
return defaultvalue; | |||||
} | |||||
} | |||||
/** | |||||
* 考虑使用中的精度,判断一个Value是否>0,实际是>0.00001 | |||||
* | |||||
* @param value double类型 | |||||
* @return boolean | |||||
*/ | |||||
public static boolean isBigThanZero(double value) { | |||||
return (value > 0.00001); | |||||
} | |||||
/** | |||||
* 考虑使用中的精度,判断一个Value是否>0,实际是>0.00001 | |||||
* | |||||
* @param value String类型 | |||||
* @return boolean | |||||
*/ | |||||
public static boolean isBigThanZero(String value) { | |||||
return !PubUtil.isEmpty(value) && isBigThanZero(toDouble(value)); | |||||
} | |||||
/** | |||||
* 考虑使用中的精度,判断一个Value是否=0,实际是给出一个值范围。 | |||||
* | |||||
* @param value double类型 | |||||
* @return boolean | |||||
*/ | |||||
public static boolean isEqualsZero(double value) { | |||||
return (-0.00001 < value && value < 0.00001); | |||||
} | |||||
/** | |||||
* 考虑使用中的精度,判断一个Value是否=0,实际是给出一个值范围。 | |||||
* | |||||
* @param value String类型 | |||||
* @return boolean | |||||
*/ | |||||
public static boolean isEqualsZero(String value) { | |||||
return PubUtil.isEmpty(value) || isEqualsZero(toDouble(value)); | |||||
} | |||||
/** | |||||
* 是否是负数 | |||||
* | |||||
* @param db_val 要判断的double | |||||
* @return 负数则返回true; | |||||
*/ | |||||
public static boolean isNegative(double db_val) { | |||||
return (compare(db_val, 0.00D) == -1); | |||||
} | |||||
/** | |||||
* 是否是正数 | |||||
* | |||||
* @param db_val 要判断的double | |||||
* @return 正数则返回true; | |||||
*/ | |||||
public static boolean isPlus(double db_val) { | |||||
return (compare(db_val, 0.00D) == 1); | |||||
} | |||||
/** | |||||
* 得到金额字符串,保持小数点2位 | |||||
* | |||||
* @param db 将double转换为金额字符串; | |||||
* @return 金额字符串#0.00; | |||||
*/ | |||||
public static String toStdNumberString(double db) { | |||||
try { | |||||
return stdNumberFormat.format(db); | |||||
} catch (Exception e) { | |||||
return "0.00"; | |||||
} | |||||
} | |||||
public static String toStdNumberStringEx(double db) { | |||||
try { | |||||
if (compare(db, -1d) == 0) return "-"; | |||||
return stdNumberFormat.format(db); | |||||
} catch (Exception e) { | |||||
return "0.00"; | |||||
} | |||||
} | |||||
/** | |||||
* 将金额格式字符串,如23,333,093.01 去掉逗号 | |||||
* | |||||
* @param s 金额串 | |||||
* @return String 去掉逗号后的串,如果amount为空,则返回0.00 | |||||
*/ | |||||
public static String toStdNumberString(String s) { | |||||
if (PubUtil.isEmpty(s)) | |||||
return "0.00"; | |||||
return stdNumberFormat.format(todouble(s)); | |||||
} | |||||
/** | |||||
* 将数据转换为两位小数的数字格式; | |||||
* | |||||
* @param d 数据 | |||||
* @param isZeroToEmpty 如果未0,是否返回“”; | |||||
* @return 两位小数的字符串; | |||||
*/ | |||||
public static String toStdNumberString(double d, boolean isZeroToEmpty) { | |||||
if (isEqualsZero(d)) { | |||||
return isZeroToEmpty ? "": "0.00"; | |||||
} | |||||
return stdNumberFormat.format(d); | |||||
} | |||||
public static String toStdNumberString(String s, boolean isZeroToEmpty) { | |||||
return toStdNumberString(todouble(s), isZeroToEmpty); | |||||
} | |||||
public static String toStdNumberString(double d, int scale) { | |||||
DecimalFormat dfn = null; | |||||
if (scale == 1) dfn = df1Format; | |||||
if (scale == 2) dfn = df2Format; | |||||
else if (scale == 4) dfn = df4; | |||||
else if (scale == 6) dfn = df6NumberF; | |||||
else if (scale <= 0) dfn = dfLong; | |||||
else { | |||||
StringBuilder sb = new StringBuilder("###,###,###,###,##0."); | |||||
for (int i = 0; i < scale; i++) sb.append("0"); | |||||
dfn = new DecimalFormat(sb.toString()); | |||||
} | |||||
return dfn.format(d); | |||||
} | |||||
/** | |||||
* 将数字乘100,保留小数点后两位, 然后后面添加% | |||||
* | |||||
* @param d 值 | |||||
* @param isZeroToEmpty,如果值为0,是否返回空; | |||||
* @return 字符串; | |||||
*/ | |||||
public static String toStdPercentNumberStr(double d, boolean isZeroToEmpty) { | |||||
if (d > -0.00000000001 && d < 0.00000000001) { | |||||
return isZeroToEmpty ? "": "0.00%"; | |||||
} | |||||
return toStdNumberString(d * 100) + "%"; | |||||
} | |||||
public static String toStdAmountString(double d) { | |||||
return toStdAmountString(d, false); | |||||
} | |||||
/** | |||||
* 将数据转换为两位小数的金额格式,带逗号; | |||||
* | |||||
* @param d 数据 | |||||
* @param isZeroToEmpty 如果未0,是否返回“”; | |||||
* @return 金额格式的字符串; | |||||
*/ | |||||
public static String toStdAmountString(double d, boolean isZeroToEmpty) { | |||||
if (isEqualsZero(d)) { | |||||
return isZeroToEmpty ? "": "0.00"; | |||||
} | |||||
return stdAmountFormat.format(d); | |||||
} | |||||
public static String toStdAmountString(String s) { | |||||
return toStdAmountString(todouble(s), false); | |||||
} | |||||
public static String toStdAmountString(String s, boolean isZeroToEmpty) { | |||||
return toStdAmountString(todouble(s), isZeroToEmpty); | |||||
} | |||||
/** | |||||
* 将小写金额转换为人民币大写金额 | |||||
* | |||||
* @param s 金额格式的串 | |||||
* @return String 转换结果 | |||||
*/ | |||||
public static String toCapsAmountString(String s) { | |||||
if (PubUtil.isEmpty(s)) return ""; | |||||
return toCapsAmountString(todouble(s)); | |||||
} | |||||
/** | |||||
* 将小写金额转换为人民币大写金额 | |||||
* | |||||
* @param v double | |||||
* @return String 转换结果 | |||||
*/ | |||||
public static String toCapsAmountString(double v) { | |||||
if (v < MIN_VALUE || v > MAX_VALUE) return "参数非法!"; | |||||
boolean negative = isNegative(v); | |||||
if (negative) v = Math.abs(v); | |||||
long l = Math.round(v * 100); | |||||
if (l == 0) return "零元整"; | |||||
String strValue = String.valueOf(l); | |||||
// i用来控制数 | |||||
int i = 0; | |||||
// j用来控制单位 | |||||
int j = UNIT.length() - strValue.length(); | |||||
StringBuilder rs = new StringBuilder(32); | |||||
boolean isZero = false; | |||||
for (; i < strValue.length(); i++, j++) { | |||||
char ch = strValue.charAt(i); | |||||
if (ch == '0') { | |||||
isZero = true; | |||||
if (UNIT.charAt(j) == '亿' || UNIT.charAt(j) == '万' || UNIT.charAt(j) == '元') { | |||||
rs.append(UNIT.charAt(j)); | |||||
isZero = false; | |||||
} | |||||
} else { | |||||
if (isZero) { | |||||
rs.append('零'); | |||||
isZero = false; | |||||
} | |||||
rs.append(DIGIT.charAt(ch - '0')).append(UNIT.charAt(j)); | |||||
} | |||||
} | |||||
if (rs.charAt(rs.length() - 1) != '分') | |||||
rs.append('整'); | |||||
i = rs.indexOf("亿万"); | |||||
if (i > 0) rs.delete(i + 1, i + 2); // i+1 ->万 | |||||
if (negative) | |||||
return rs.insert(0, '负').toString(); | |||||
else | |||||
return rs.toString(); | |||||
} | |||||
/** | |||||
* 返回0 到 maxvalue的随机数 | |||||
* | |||||
* @param maxvalue 随机数的最大值 | |||||
* @return int | |||||
*/ | |||||
public static int rnd(int maxvalue) { | |||||
return (int) (Math.random() * (maxvalue + 1)); | |||||
} | |||||
public static double chkDbNull(Double v) { | |||||
return v == null ? 0: v; | |||||
} | |||||
public static double max(double d1, double d2) { | |||||
return compare(d1, d2) < 0 ? d2 : d1; | |||||
} | |||||
public static double min(double d1, double d2) { | |||||
return compare(d1, d2) < 0 ? d1 : d2; | |||||
} | |||||
public static void main(String[] args) { | |||||
double aa=123456789.345678900005; | |||||
System.out.println("args0 = " + upDouble(aa,0)); | |||||
System.out.println("args1 = " + upDouble(aa,1)); | |||||
System.out.println("args2 = " + upDouble(aa,2)); | |||||
System.out.println("args3 = " + upDouble(aa,3)); | |||||
System.out.println("args4 = " + upDouble(aa,4)); | |||||
System.out.println("args5 = " + upDouble(aa,5)); | |||||
System.out.println("args5 = " + upDouble(aa,6)); | |||||
System.out.println("args5 = " + upDouble(aa,7)); | |||||
System.out.println("args5 = " + upDouble(aa,8)); | |||||
} | |||||
/** | |||||
* double 去尾法 | |||||
* @param src 待处理数据 | |||||
* @param scale 保留小数位数 | |||||
* @return | |||||
*/ | |||||
public static double cutDouble(double src, int scale){ | |||||
String v = toStdNumberString(src, 6);//先到6位小数,再去计算,否则容易出错,如8.3成8.29999999999,舍位就成了8.29了 | |||||
DecimalFormat formater = new DecimalFormat(); | |||||
formater.setMaximumFractionDigits(scale); | |||||
formater.setGroupingSize(0); | |||||
formater.setRoundingMode(RoundingMode.FLOOR); | |||||
return new BigDecimal(formater.format(toDouble(v))).doubleValue(); | |||||
} | |||||
/** | |||||
* double 进位法 | |||||
* @param src 待处理数据 | |||||
* @param scale 保留小数位数 | |||||
* @return | |||||
*/ | |||||
public static double upDouble(double src, int scale){ | |||||
String v = toStdNumberString(src, 6);//先到6位小数,再去计算 | |||||
DecimalFormat formater = new DecimalFormat(); | |||||
formater.setMaximumFractionDigits(scale); | |||||
formater.setGroupingSize(0); | |||||
formater.setRoundingMode(RoundingMode.UP); | |||||
return new BigDecimal(formater.format(toDouble(v))).doubleValue(); | |||||
} | |||||
} |
@@ -0,0 +1,377 @@ | |||||
package cc.smtweb.framework.core.util; | |||||
import java.util.HashMap; | |||||
import java.util.Map; | |||||
import java.util.regex.Pattern; | |||||
/** | |||||
* 个人身份证帮助类 | |||||
* | |||||
* @author : AKzz | |||||
* @version : $Revision:$ | |||||
*/ | |||||
public final class PersonUIDUtil { | |||||
private final static String uid_chars = "0123456789XZ"; | |||||
private static Map<String, String> map_uid_chars; | |||||
static { | |||||
map_uid_chars = new HashMap<>(); | |||||
map_uid_chars.put("0", "0"); | |||||
map_uid_chars.put("1", "1"); | |||||
map_uid_chars.put("2", "2"); | |||||
map_uid_chars.put("3", "3"); | |||||
map_uid_chars.put("4", "4"); | |||||
map_uid_chars.put("5", "5"); | |||||
map_uid_chars.put("6", "6"); | |||||
map_uid_chars.put("7", "7"); | |||||
map_uid_chars.put("8", "8"); | |||||
map_uid_chars.put("9", "9"); | |||||
map_uid_chars.put("X", "X"); | |||||
map_uid_chars.put("x", "X"); | |||||
map_uid_chars.put("Z", "Z"); | |||||
map_uid_chars.put("z", "Z"); | |||||
} | |||||
/* | |||||
大陆的身份证为18位,老的身份证是15位。 | |||||
地址码(身份证前六位)第一、第二数字表示公民所在地的省份(或自治区、直辖市); | |||||
第三、第四位数字表示公民 所在地的市(或州); | |||||
第五、第六位数字表示公民所在地的县(或县级市); | |||||
生日期码(身份证第七位到第十四位)接下来的8位数字表示公民的出生年、月、日; | |||||
顺序码(身份证第十五位到十七位)为同一地址码所标识的区域范围内,对同年、月、日出生的人员编定的顺序号 | |||||
第17位:奇数为男性,偶数为女性) | |||||
第十八位数字的计算方法为: | |||||
1.将前面的身份证号码17位数分别乘以不同的系数。从第一位到第十七位的系数分别为:7 9 10 5 8 4 2 1 6 3 7 9 10 5 8 4 2 | |||||
2.将这17位数字和系数相乘的结果相加。 | |||||
3.用加出来和除以11,看余数是多少? | |||||
4.余数只可能有0 1 2 3 4 5 6 7 8 9 10这11个数字。其分别对应的最后一位身份证的号码为'1', '0', 'X', '9', '8', '7', '6', '5', '4', '3', '2' | |||||
*/ | |||||
public final static int NEW_CARD_NUMBER_LENGTH = 18; | |||||
public final static int OLD_CARD_NUMBER_LENGTH = 15; | |||||
// 18位身份证中,各个数字的生成校验码时的权值 | |||||
private final static int[] VERIFY_CODE_WEIGHT = {7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2}; | |||||
// 18位身份证中最后一位校验码 | |||||
private final static char[] VERIFY_CODE = {'1', '0', 'X', '9', '8', '7', '6', '5', '4', '3', '2'}; | |||||
public static boolean checkPersonUID(String uid) { | |||||
return checkPersonUIDA(uid, false); | |||||
} | |||||
/** | |||||
* 检查身份证是否合法. | |||||
*/ | |||||
public static boolean checkPersonUIDA(String uid, boolean include15) { | |||||
String uid_15_ex = "^\\d{6}\\d{2}(0[1-9]|10|11|12)(0[1-9]|1[0-9]|2[0-9]|3[0-1])\\d{3}$"; | |||||
String uid_18_ex = "^\\d{6}(19|20)\\d{2}(0[1-9]|10|11|12)(0[1-9]|1[0-9]|2[0-9]|3[0-1])\\d{3}[0-9X]{1}$"; | |||||
String regx, bdate; | |||||
if (include15 && uid.length() == 15) { | |||||
regx = uid_15_ex; // 15位 地址码 + (年+月+日) + 顺序号 | |||||
bdate = "19" + uid.substring(6, 12); | |||||
} else if (uid.length() == NEW_CARD_NUMBER_LENGTH) { | |||||
regx = uid_18_ex; // 18位 身份证 | |||||
bdate = uid.substring(6, 14); | |||||
} else { | |||||
return false; | |||||
} | |||||
if (!DateUtil.isDateFormat(bdate, "YYYYMMDD")) return false; | |||||
Pattern pattern = Pattern.compile(regx); | |||||
boolean ret = pattern.matcher(uid).matches(); | |||||
if (ret && uid.length() == NEW_CARD_NUMBER_LENGTH) { | |||||
return calculateVerifyCode(uid) == uid.charAt(NEW_CARD_NUMBER_LENGTH - 1); | |||||
} | |||||
return ret; | |||||
} | |||||
/** | |||||
* 检查身份证是否合法 | |||||
* | |||||
* @param uid 要检查的身份证号; | |||||
* @return 对于可以转换的自动验证转换为正确的身份证号,如18位51012719731204001X,则能自动转换为正确的,15位自动转换为18位,返回的message中。 | |||||
*/ | |||||
public static boolean checkPersonUIDEx(String uid) { | |||||
return checkPersonUIDExA(uid, false); | |||||
} | |||||
public static boolean checkPersonUIDExA(String uid, boolean include15) { | |||||
String uid_15_ex = "^\\d{6}\\d{2}(0[1-9]|10|11|12)(0[1-9]|1[0-9]|2[0-9]|3[0-1])\\d{3}$"; | |||||
String uid_18_ex = "^\\d{6}(19|20)\\d{2}(0[1-9]|10|11|12)(0[1-9]|1[0-9]|2[0-9]|3[0-1])\\d{3}[0-9A-Z]{1}$"; | |||||
String regx, bdate; //11011720031031501Z | |||||
if (include15 && uid.length() == 15) { | |||||
regx = uid_15_ex; // 15位 地址码 + (年+月+日) + 顺序号 | |||||
bdate = "19" + uid.substring(6, 12); | |||||
} else if (uid.length() == NEW_CARD_NUMBER_LENGTH) { | |||||
regx = uid_18_ex; // 18位 身份证 | |||||
bdate = uid.substring(6, 14); | |||||
} else { | |||||
return false; | |||||
} | |||||
if (!DateUtil.isDateFormat(bdate, "YYYYMMDD")) { | |||||
return false; | |||||
} | |||||
Pattern pattern = Pattern.compile(regx); | |||||
boolean ret = pattern.matcher(uid).matches(); | |||||
if (!ret) { | |||||
return false; | |||||
} | |||||
if (uid.length() == NEW_CARD_NUMBER_LENGTH) {//18位 | |||||
char c = calculateVerifyCode(uid); | |||||
if (c == uid.charAt(NEW_CARD_NUMBER_LENGTH - 1)) | |||||
return true;//正确 | |||||
return false;//错误 | |||||
} else {//15位则换算成18位 | |||||
return true; | |||||
} | |||||
} | |||||
/** | |||||
* 校验码(第十八位数): | |||||
* 十七位数字本体码加权求和公式 S = Sum(Ai * Wi), i = 0...16 ,先对前17位数字的权求和; | |||||
* Ai:表示第i位置上的身份证号码数字值 Wi:表示第i位置上的加权因子 Wi: 7 9 10 5 8 4 2 1 6 3 7 9 10 5 8 4 | |||||
* 2; | |||||
* 计算模 Y = mod(S, 11)< | |||||
* 通过模得到对应的校验码 Y: 0 1 2 3 4 5 6 7 8 9 10 校验码: 1 0 X 9 8 7 6 5 4 3 2 | |||||
*/ | |||||
public static char calculateVerifyCode(CharSequence uid) { | |||||
int sum = 0; | |||||
for (int i = 0; i < NEW_CARD_NUMBER_LENGTH - 1; i++) { | |||||
char ch = uid.charAt(i); | |||||
sum += (ch - '0') * VERIFY_CODE_WEIGHT[i]; | |||||
} | |||||
return VERIFY_CODE[sum % 11]; | |||||
} | |||||
/** | |||||
* 获取身份证的第17位,奇数为男性,偶数为女性 | |||||
* | |||||
* @param uid 身份证号; | |||||
* @return 0: 女; 1.男; | |||||
*/ | |||||
public static int getPersonSex(CharSequence uid) { | |||||
char genderCode; | |||||
if (uid.length() == NEW_CARD_NUMBER_LENGTH) | |||||
genderCode = uid.charAt(NEW_CARD_NUMBER_LENGTH - 2); | |||||
/*else if (uid.length() == OLD_CARD_NUMBER_LENGTH) | |||||
genderCode = uid.charAt(OLD_CARD_NUMBER_LENGTH - 1);*/ | |||||
else | |||||
return -1;//throw new IllegalArgumentException("非法的居民身份证号[" + uid + "]!"); | |||||
return (genderCode - '0' & 0x1) == 0x01 ? 1 : 0; | |||||
} | |||||
/** | |||||
* 从身份证中取得出身日期 | |||||
*/ | |||||
public static String getBirthday(CharSequence uid) { | |||||
StringBuilder birthday = new StringBuilder(10); | |||||
/*if (uid.length() == OLD_CARD_NUMBER_LENGTH) { | |||||
birthday.append("19").append(uid.subSequence(6, 8)).append('-'); | |||||
birthday.append(uid.subSequence(8, 10)).append('-'); | |||||
birthday.append(uid.subSequence(10, 12)); | |||||
} else */ | |||||
if (uid.length() == NEW_CARD_NUMBER_LENGTH) { | |||||
birthday.append(uid.subSequence(6, 10)).append('-'); | |||||
birthday.append(uid.subSequence(10, 12)).append('-'); | |||||
birthday.append(uid.subSequence(12, 14)); | |||||
} else { | |||||
throw new IllegalArgumentException("非法的居民身份证号[" + uid + "]!"); | |||||
} | |||||
return birthday.toString(); | |||||
} | |||||
/** | |||||
* 把15位身份证号码转换到18位身份证号码<br> | |||||
* 15位身份证号码与18位身份证号码的区别为:<br> | |||||
* 1、15位身份证号码中,"出生年份"字段是2位,转换时需要补入"19",表示20世纪<br> | |||||
* 2、15位身份证无最后一位校验码。18位身份证中,校验码根据根据前17位生成 | |||||
*/ | |||||
public static String contertToNewCardNumber(String oldUID) { | |||||
if (oldUID.length() != 15) { | |||||
char c = calculateVerifyCode(oldUID); | |||||
return oldUID.substring(0, NEW_CARD_NUMBER_LENGTH - 1) + c; | |||||
} | |||||
StringBuilder buf = new StringBuilder(NEW_CARD_NUMBER_LENGTH); | |||||
buf.append(oldUID.substring(0, 6)); | |||||
buf.append("19"); | |||||
buf.append(oldUID.substring(6)); | |||||
buf.append(calculateVerifyCode(buf)); | |||||
return buf.toString().toUpperCase(); | |||||
} | |||||
/** | |||||
* 根据身份证和传入的年月,计算人员年龄; | |||||
* | |||||
* @param person_uid 身份证号 | |||||
* @param curYear 年度 | |||||
* @param curMonth 月份 | |||||
*/ | |||||
public static int getPersonAge(String person_uid, int curYear, int curMonth) { | |||||
String birth_date = getBirthday(person_uid); | |||||
int year = Integer.parseInt(birth_date.substring(0, 4)); | |||||
int month = Integer.parseInt(birth_date.substring(5, 7)); | |||||
int age = curYear - year; | |||||
if (curMonth < month) | |||||
age--; | |||||
return age; | |||||
} | |||||
public static int getPersonAge(String person_uid, String period) { | |||||
int y = Integer.parseInt(period.substring(0, 4)); | |||||
int m = Integer.parseInt(period.substring(4)); | |||||
return getPersonAge(person_uid, y, m); | |||||
} | |||||
/** | |||||
* 根据身份证和传入的年月,计算人员年龄; | |||||
* | |||||
* @param person_uid 身份证号 | |||||
* @param nowDate 比较日期 2017-01-01 | |||||
*/ | |||||
public static int getPersonAgeEx(String person_uid, String nowDate, int ageType) { | |||||
int y = Integer.parseInt(nowDate.substring(0, 4)); | |||||
int m = Integer.parseInt(nowDate.substring(5, 7)); | |||||
int d = Integer.parseInt(nowDate.substring(8, 10)); | |||||
String birth_date = getBirthday(person_uid); | |||||
int year = Integer.parseInt(birth_date.substring(0, 4)); | |||||
int month = Integer.parseInt(birth_date.substring(5, 7)); | |||||
int day = Integer.parseInt(birth_date.substring(8, 10)); | |||||
int age = y - year; | |||||
if (ageType == 0) { | |||||
if (m < month) age--; | |||||
} else if (ageType == 4) { | |||||
if (m < month || (m == month && d < day)) age--; | |||||
else age++; | |||||
} else if (ageType == 2) { | |||||
age++; | |||||
} else if (ageType == 3) { | |||||
age--; | |||||
} | |||||
return age; | |||||
} | |||||
public static int getPersonAge(String person_uid, String period, int ageType) { | |||||
int y = Integer.parseInt(period.substring(0, 4)); | |||||
int m = Integer.parseInt(period.substring(4)); | |||||
String birth_date = getBirthday(person_uid); | |||||
int year = Integer.parseInt(birth_date.substring(0, 4)); | |||||
int month = Integer.parseInt(birth_date.substring(5, 7)); | |||||
int age = y - year; | |||||
if (ageType == 0) { | |||||
if (m < month) age--; | |||||
} else if (ageType == 2) { | |||||
age++; | |||||
} else if (ageType == 3) { | |||||
age--; | |||||
} | |||||
return age; | |||||
} | |||||
public static int getPersonAge(String person_uid, int year, int month, int ageType) { | |||||
String birth_date = getBirthday(person_uid); | |||||
int y = Integer.parseInt(birth_date.substring(0, 4)); | |||||
int m = Integer.parseInt(birth_date.substring(5, 7)); | |||||
int age = year - y; | |||||
if (ageType == 0) { | |||||
if (month < m) age--; | |||||
} else if (ageType == 2) { | |||||
age++; | |||||
} else if (ageType == 3) { | |||||
age--; | |||||
} | |||||
return age; | |||||
} | |||||
//计算年龄,按年算 | |||||
public static int getPersonAgeYear(String person_uid, int curYear) { | |||||
String birth_date = getBirthday(person_uid); | |||||
int year = Integer.parseInt(birth_date.substring(0, 4)); | |||||
return curYear - year; | |||||
} | |||||
public static int getPersonAgeYear(String person_uid, String period) { | |||||
int y = Integer.parseInt(period.substring(0, 4)); | |||||
return getPersonAgeYear(person_uid, y); | |||||
} | |||||
/** | |||||
* 根据身份证,根据当前年月,计算人员年龄; | |||||
* | |||||
* @param person_uid 身份证号 | |||||
*/ | |||||
public static int getPersonAge(String person_uid) { | |||||
String birth_date = getBirthday(person_uid); | |||||
int year = Integer.parseInt(birth_date.substring(0, 4)); | |||||
int month = Integer.parseInt(birth_date.substring(5, 7)); | |||||
int age = Integer.parseInt(DateUtil.nowYear()) - year; | |||||
if (Integer.parseInt(DateUtil.nowMonth()) < month) | |||||
age--; | |||||
return age; | |||||
} | |||||
//去掉非法字符 | |||||
public static String cleanPersonUid(String personUid) { | |||||
if (personUid == null) return ""; | |||||
personUid = personUid.trim().toUpperCase(); | |||||
StringBuilder sb = new StringBuilder(personUid.length()); | |||||
for (int len = personUid.length(), i = 0; i < len; i++) { | |||||
char c = personUid.charAt(i); | |||||
if (c == 'X' || (c >= '0' && c <= '9')) sb.append(c); | |||||
} | |||||
return sb.toString(); | |||||
} | |||||
//去掉非法字符,含z | |||||
public static String cleanPersonUidEx(String personUid) { | |||||
if (personUid == null) return ""; | |||||
personUid = personUid.trim().toUpperCase(); | |||||
StringBuilder sb = new StringBuilder(18); | |||||
String s; | |||||
for (int len = personUid.length(), i = 0; i < len; i++) { | |||||
char c = personUid.charAt(i); | |||||
if (uid_chars.indexOf(c) >= 0) sb.append(c); | |||||
else { | |||||
s = String.valueOf(c); | |||||
if (map_uid_chars.containsKey(s)) sb.append(map_uid_chars.get(s)); | |||||
} | |||||
} | |||||
return sb.toString(); | |||||
} | |||||
/** | |||||
* 显示uid的时候保密,用一些**符号 | |||||
* @param person_uid | |||||
* @return | |||||
*/ | |||||
public static String secretPersonUID(String person_uid){ | |||||
return secretPersonUID(person_uid,8); | |||||
} | |||||
public static String secretPersonUID(String person_uid,int secretLength){ | |||||
if(person_uid.length()>14){ | |||||
String head = person_uid.substring(0,6); | |||||
String tail = person_uid.substring(14,person_uid.length()); | |||||
StringBuilder sb = new StringBuilder(); | |||||
sb.append(head); | |||||
int i=0; | |||||
while (i<secretLength){ | |||||
sb.append("*"); | |||||
i++; | |||||
} | |||||
sb.append(tail); | |||||
return sb.toString(); | |||||
}else return person_uid; | |||||
} | |||||
public static void main(String[] args) { | |||||
} | |||||
} |
@@ -0,0 +1,129 @@ | |||||
package cc.smtweb.framework.core.util; | |||||
import org.apache.commons.codec.binary.Base64; | |||||
import javax.crypto.Cipher; | |||||
import java.security.*; | |||||
import java.security.interfaces.RSAPrivateKey; | |||||
import java.security.interfaces.RSAPublicKey; | |||||
import java.security.spec.PKCS8EncodedKeySpec; | |||||
import java.security.spec.X509EncodedKeySpec; | |||||
/** | |||||
* Created by Akmm at 2020/4/23 15:23 | |||||
*/ | |||||
public class RSAUtil { | |||||
private static final KeyPair keyPair = initKey(); | |||||
private static KeyPair initKey() { | |||||
try { | |||||
KeyPairGenerator keyPairGen = KeyPairGenerator.getInstance("RSA"); | |||||
keyPairGen.initialize(1024, new SecureRandom()); | |||||
// 生成一个密钥对,保存在keyPair中 | |||||
return keyPairGen.generateKeyPair(); | |||||
} catch (Exception e) { | |||||
throw new RuntimeException(e); | |||||
} | |||||
} | |||||
public static String generateBase64PublicKey() { | |||||
PublicKey publicKey = keyPair.getPublic(); | |||||
return new String(Base64.encodeBase64(publicKey.getEncoded())); | |||||
} | |||||
public static String generateBase64PrvKey() { | |||||
PrivateKey privkey = keyPair.getPrivate(); | |||||
return new String(Base64.encodeBase64(privkey.getEncoded())); | |||||
} | |||||
public static String decryptBase64(String string) throws Exception { | |||||
byte[] byteArray = Base64.decodeBase64(string.getBytes()); | |||||
Cipher cipher = Cipher.getInstance("RSA"); | |||||
PrivateKey privateKey = keyPair.getPrivate(); | |||||
cipher.init(Cipher.DECRYPT_MODE, privateKey); | |||||
byte[] plainText = cipher.doFinal(byteArray); | |||||
return new String(plainText); | |||||
} | |||||
/** | |||||
* 利用我们提供的密钥加密 | |||||
* | |||||
* @param str | |||||
* @return | |||||
* @throws Exception | |||||
*/ | |||||
public static String encryptBase64(String str) throws Exception { | |||||
PublicKey pubKey = keyPair.getPublic(); | |||||
//RSA加密 | |||||
Cipher cipher = Cipher.getInstance("RSA"); | |||||
cipher.init(Cipher.ENCRYPT_MODE, pubKey); | |||||
return Base64.encodeBase64String(cipher.doFinal(str.getBytes("UTF-8"))); | |||||
} | |||||
/** | |||||
* 指定RSA公钥加密 | |||||
* | |||||
* @param str 加密字符串 | |||||
* @param publicKey 公钥 | |||||
* @return 密文 | |||||
* @throws Exception 加密过程中的异常信息 | |||||
*/ | |||||
public static String encryptBase64(String str, String publicKey) throws Exception { | |||||
//base64编码的公钥 | |||||
byte[] decoded = Base64.decodeBase64(publicKey); | |||||
RSAPublicKey pubKey = (RSAPublicKey) KeyFactory.getInstance("RSA").generatePublic(new X509EncodedKeySpec(decoded)); | |||||
//RSA加密 | |||||
Cipher cipher = Cipher.getInstance("RSA"); | |||||
cipher.init(Cipher.ENCRYPT_MODE, pubKey); | |||||
return Base64.encodeBase64String(cipher.doFinal(str.getBytes("UTF-8"))); | |||||
} | |||||
/** | |||||
* 指定RSA私钥解密 | |||||
* | |||||
* @param str 加密字符串 | |||||
* @param privateKey 私钥 | |||||
* @return 铭文 | |||||
* @throws Exception 解密过程中的异常信息 | |||||
*/ | |||||
public static String decryptBase64(String str, String privateKey) throws Exception { | |||||
//64位解码加密后的字符串 | |||||
byte[] inputByte = Base64.decodeBase64(str.getBytes("UTF-8")); | |||||
//base64编码的私钥 | |||||
byte[] decoded = Base64.decodeBase64(privateKey); | |||||
RSAPrivateKey priKey = (RSAPrivateKey) KeyFactory.getInstance("RSA").generatePrivate(new PKCS8EncodedKeySpec(decoded)); | |||||
//RSA解密 | |||||
Cipher cipher = Cipher.getInstance("RSA"); | |||||
cipher.init(Cipher.DECRYPT_MODE, priKey); | |||||
String outStr = new String(cipher.doFinal(inputByte)); | |||||
return outStr; | |||||
} | |||||
public static void main(String[] args) throws Exception { | |||||
String ss = "我的123"; | |||||
/*String ss = "UR/ykQMQiLePbUFIlRYkUIaDcxDTYVOK9uTwqkbwlo6OcFzs0sQL+qzRMYBYCOC+ufLSSbQgwgbb+gxWf5GP5QyH5ygp4XHOa6IWbILHDB1nqze4S+NKhR72UOMqY5J4/C2ZZyiTQKTY5KJzn1gtjEbrzBHEFQEBTIJbg5k2zu4="; | |||||
String pk = "MIICdQIBADANBgkqhkiG9w0BAQEFAASCAl8wggJbAgEAAoGBAIBwwtBhDftNsYLUMQme/Av+RQKg32wmhkd7m2hm/CZu+FnNsWCIGt7pmCVfIdnJCgm15HjmW/alfLO5XDDacRVmL" + | |||||
"I5pvmv6jCki+BoquUMQFV3pJcgSMg/MocdACPkXSvB/m7IhDu2P3eXIx55aieLiPDciujiOD9Do5AmicM07AgMBAAECgYAha7X1fNujgYLoFQixhTH2ePJCDdQ1Ew0ruokksG96HLP4wi" + | |||||
"IeiSvcxxG0370yKzK2diL+JorVchgxt9C6UYzM8o+b4NflFCuKqfUCk63fTrBeXI0OaUFJATxxXfqzNgDaWgiqItRE/h1rBtQG5FQ0V1zFE+pLPSK+bnD6uWpFEQJBAM1x8pFOdnP8+iX" + | |||||
"brt+dHeFttOLFt8OS/TVD2ZD+NblxPYYRha89a9mLb0TkErEnQEegoA1Dq+4c+4Ayx3+nnykCQQCgC+Rr+pilMIUuJSnBbY4+Mn2cgRNhQX+w2cDpXNxtFi1eld2MjHgVbp+VmivGSDBe" + | |||||
"c/Oq7qSnEITWLxYsvSnDAkB1AZmh8ir6YjDhkN1m06fp9L5ZjTvcsgFt7aeisXVNmVXt3lrh9DxRWN1VQgP3SyCL6spc45au9WizmbgPVxsJAkAqUPqkUi3p/1o3STwxGHZzm4X6y2YEY" + | |||||
"P0SFYEcMqFVdneoepeJgdp+UDGBrLHGS2/+iUnz+AUw5v04ZFrImXthAkAfoPdHP00CFsvIK4fK/iBboDPmY014/DR+W8jfJHHu5Lv0XuYvdNsrvM9GL+UNgjNTCF0OT3UWFfq5Hrta89vZ"; | |||||
System.out.println(decryptBase64(ss, pk));*/ | |||||
String pubkey = generateBase64PublicKey(); | |||||
System.out.println("pubkey::::::::::::::" + pubkey); | |||||
PrivateKey pKey = keyPair.getPrivate(); | |||||
String prvkey = new String(Base64.encodeBase64(pKey.getEncoded())); | |||||
System.out.println("prvkey::::::" + prvkey); | |||||
System.out.println("encrypt1::::::" + encryptBase64(ss)); | |||||
String en = encryptBase64(ss, pubkey); | |||||
System.out.println("encrypt2::::::" + en); | |||||
System.out.println("decrypt1::::::" + decryptBase64(en)); | |||||
System.out.println("decrypt2::::::" + decryptBase64(encryptBase64(ss), prvkey)); | |||||
} | |||||
} |
@@ -0,0 +1,258 @@ | |||||
package cc.smtweb.framework.core.util; | |||||
import org.dom4j.*; | |||||
import org.dom4j.io.OutputFormat; | |||||
import org.dom4j.io.SAXReader; | |||||
import org.dom4j.io.XMLWriter; | |||||
import java.io.File; | |||||
import java.io.FileOutputStream; | |||||
import java.io.IOException; | |||||
import java.io.InputStream; | |||||
import java.net.MalformedURLException; | |||||
import java.net.URL; | |||||
import java.util.HashMap; | |||||
import java.util.Iterator; | |||||
import java.util.Map; | |||||
/** | |||||
* Created by Akmm at 2011-1-19 10:16:01 | |||||
*/ | |||||
public class XmlUtil { | |||||
/** | |||||
* 按缩减格式写xml文件 | |||||
* | |||||
* @param document | |||||
* @param fileName | |||||
* @throws IOException | |||||
*/ | |||||
public static void saveToFileCompact(Document document, String fileName) throws IOException { | |||||
saveToFile(document, fileName, OutputFormat.createCompactFormat()); | |||||
} | |||||
/** | |||||
* 按美化格式写xml | |||||
* | |||||
* @param document | |||||
* @param fileName | |||||
* @throws IOException | |||||
*/ | |||||
public static void saveToFilePretty(Document document, String fileName) throws IOException { | |||||
// 指定文件 美化格式 | |||||
saveToFile(document, fileName, OutputFormat.createPrettyPrint()); | |||||
} | |||||
/** | |||||
* 直接写xml,无格式 | |||||
* | |||||
* @param document | |||||
* @param fileName | |||||
* @throws IOException | |||||
*/ | |||||
public static void saveToFile(Document document, String fileName, OutputFormat format) throws IOException { | |||||
XMLWriter xmlWriter; | |||||
if (format == null) xmlWriter = new XMLWriter(new FileOutputStream(fileName)); | |||||
else xmlWriter = new XMLWriter(new FileOutputStream(fileName), format); | |||||
xmlWriter.write(document); | |||||
xmlWriter.close(); | |||||
} | |||||
/** | |||||
* 直接写xml,无格式 | |||||
* | |||||
* @param document | |||||
* @param fileName | |||||
* @throws IOException | |||||
*/ | |||||
public static void saveToFile(Document document, String fileName) throws IOException { | |||||
saveToFile(document, fileName, null); | |||||
} | |||||
/** | |||||
* 创建一个Document | |||||
* | |||||
* @return | |||||
*/ | |||||
public static Document createDocument() { | |||||
return DocumentHelper.createDocument(); | |||||
} | |||||
/** | |||||
* 解析string为一个Document | |||||
* | |||||
* @return | |||||
*/ | |||||
public static Document parseXml(String xml) throws DocumentException { | |||||
return DocumentHelper.parseText(xml); | |||||
} | |||||
public static Document readXmlDocument(String fileName) throws MalformedURLException, DocumentException { | |||||
SAXReader reader = new SAXReader(); | |||||
return reader.read(new File(fileName)); | |||||
} | |||||
public static Document readXmlDocument(InputStream file) throws MalformedURLException, DocumentException { | |||||
SAXReader reader = new SAXReader(); | |||||
return reader.read(file); | |||||
} | |||||
public static Document readXmlDocument(URL url) throws MalformedURLException, DocumentException { | |||||
SAXReader reader = new SAXReader(); | |||||
return reader.read(url); | |||||
} | |||||
public static Document readXmlDocument(File file) throws MalformedURLException, DocumentException { | |||||
SAXReader reader = new SAXReader(); | |||||
return reader.read(file); | |||||
} | |||||
//获取节点属性 | |||||
public static String getChildValue(Element e, String chileName) { | |||||
Element ec = e.element(chileName); | |||||
if (ec != null) return ec.getTextTrim(); | |||||
return null; | |||||
} | |||||
//获取节点属性 | |||||
public static String getAttribute(Element e, String attrName) { | |||||
Attribute a = e.attribute(attrName); | |||||
if (a != null) return a.getValue(); | |||||
return null; | |||||
} | |||||
//获取节点属性,转为字符串数组 | |||||
public static String[] getAttrStrArray(Element e, String attrName) { | |||||
String s = getAttribute(e, attrName); | |||||
if (PubUtil.isNotEmptyStr(s)) return StringUtil.split(s, ",").toArray(new String[]{}); | |||||
return new String[0]; | |||||
} | |||||
//获取节点属性,转为int数组 | |||||
public static int[] getAttrIntArray(Element e, String attrName) { | |||||
String[] ss = getAttrStrArray(e, attrName); | |||||
int[] ret = new int[ss.length]; | |||||
for (int i = 0, len = ss.length; i < len; i++) { | |||||
ret[i] = PubUtil.getIntIgnoreErr(ss[i]); | |||||
} | |||||
return ret; | |||||
} | |||||
public static int getAttributeInt(Element e, String attrName) { | |||||
return PubUtil.getIntIgnoreErr(getAttribute(e, attrName)); | |||||
} | |||||
public static double getAttributeDbl(Element e, String attrName) { | |||||
return PubUtil.getDoubleIgnoreErr(getAttribute(e, attrName)); | |||||
} | |||||
public static boolean getAttributeBool(Element e, String attrName) { | |||||
String s = getAttribute(e, attrName); | |||||
return "1".equals(s) || "Y".equalsIgnoreCase(s) || "true".equalsIgnoreCase(s) || "yes".equalsIgnoreCase(s); | |||||
} | |||||
//获取节点属性 | |||||
public static String getAttributeIgnoreNull(Element e, String attrName) { | |||||
return PubUtil.checkNull(getAttribute(e, attrName)); | |||||
} | |||||
//读取节点所有属性,返回map | |||||
public static Map<String, String> getAttributeMap(Element e) { | |||||
Map<String, String> map = new HashMap<>(); | |||||
for (Iterator as = e.attributeIterator(); as.hasNext(); ) { | |||||
Attribute a = (Attribute) as.next(); | |||||
map.put(a.getName(), a.getValue()); | |||||
} | |||||
return map; | |||||
} | |||||
public static void removeAttribute(Element e, String attrName) { | |||||
Attribute a = e.attribute(attrName); | |||||
if (a != null) e.remove(a); | |||||
} | |||||
//设置节点属性 | |||||
public static void setAttribute(Element e, String attrName, String attrValue) { | |||||
if (PubUtil.isNotEmpty(attrValue)) e.addAttribute(attrName, attrValue); | |||||
else removeAttribute(e, attrName); | |||||
} | |||||
//设置节点属性 | |||||
public static void setAttribute(Element e, String attrName, int attrValue) { | |||||
if (attrValue != 0) e.addAttribute(attrName, String.valueOf(attrValue)); | |||||
else removeAttribute(e, attrName); | |||||
} | |||||
//设置节点属性 | |||||
public static void setAttribute(Element e, String attrName, double attrValue) { | |||||
if (!MathUtil.isEqualsZero(attrValue)) e.addAttribute(attrName, String.valueOf(attrValue)); | |||||
else removeAttribute(e, attrName); | |||||
} | |||||
//设置节点属性 | |||||
public static void setAttribute(Element e, String attrName, boolean attrValue) { | |||||
if (attrValue) e.addAttribute(attrName, "1"); | |||||
else removeAttribute(e, attrName); | |||||
} | |||||
//设置节点属性 | |||||
public static void removeElement(Element parent, String name) { | |||||
Element e = parent.element(name); | |||||
if (e != null) parent.remove(e); | |||||
} | |||||
//解析节点到Map | |||||
public static void decodeForMap(Element pnode, Map<String, String> map) { | |||||
for (Iterator it = pnode.elementIterator(); it.hasNext(); ) { | |||||
Element el = (Element) it.next(); | |||||
String nodename = el.getName(); | |||||
map.put(nodename, el.getTextTrim()); | |||||
} | |||||
} | |||||
//解析节点到Map | |||||
public static void writeMap(Element pnode, Map<String, Object> map) { | |||||
for (String s: map.keySet()) { | |||||
Element e = pnode.addElement(s); | |||||
final Object o = map.get(s); | |||||
e.setText(o != null ? o.toString() : ""); | |||||
} | |||||
} | |||||
//添加节点 | |||||
public static void addNode(Element pnode, String name, Object value){ | |||||
Element e = pnode.addElement(name); | |||||
e.setText(value != null ? value.toString() : ""); | |||||
} | |||||
public static void main(String[] args) { | |||||
try { | |||||
Document doc = readXmlDocument("f:\\temp\\plugin-developer.xml"); | |||||
Element e = doc.getRootElement(); | |||||
System.out.println("id:::::::" + getAttribute(e, "id")); | |||||
System.out.println("name:::::::" + getAttribute(e, "name")); | |||||
System.out.println("vvvv:::::::" + getAttribute(e, "呵呵")); | |||||
// e.accept(new VisitorSupport() { | |||||
// public void visit(Element element) { | |||||
// System.out.println(element.getName() + ":::eee:::" + element.getText()); | |||||
// } | |||||
// | |||||
// public void visit(Attribute a) { | |||||
// System.out.println(a.getName() + ":::aaa:::" + a.getValue()); | |||||
// } | |||||
// }); | |||||
// 枚举所有子节点 | |||||
Element e1 = e.element("fields"); | |||||
e1 = e1.element("field"); | |||||
System.out.println(getAttributeIgnoreNull(e1, "id")); | |||||
setAttribute(e, "vvvv", "tttttttt"); | |||||
//e.addCDATA("<a>asdasd</a>"); | |||||
saveToFileCompact(doc, "f:\\temp\\plugin-developer1.xml"); | |||||
saveToFilePretty(doc, "f:\\temp\\plugin-developer2.xml"); | |||||
saveToFile(doc, "f:\\temp\\plugin-developer3.xml"); | |||||
} catch (Exception e1) { | |||||
e1.printStackTrace(); | |||||
} | |||||
} | |||||
} |