package com.zzwtec.third.utils; import org.apache.commons.lang3.StringUtils; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import java.text.ParseException; import java.text.SimpleDateFormat; import java.time.LocalDateTime; import java.util.Calendar; import java.util.Date; import static java.util.Calendar.*; /** * create by Jomchen on 2018/11/29 */ public class TimeUtil { public static final long defaultYearMonthDay = 10000101; // 1000年01月01日 // yyyy-MM-dd HH:mm:ss public static final String NOW_TIME_1 = "yyyy-MM-dd HH:mm:ss"; // yyyyMMddHHmmss public static final String NOW_TIME_2 = "yyyyMMddHHmmss"; // yyyyMMddHHmmss public static final String NOW_TIME_3 = "yyyyMMddHHmm"; // yyyyMMdd public static final String THIS_DAY_TIME = "yyyyMMdd"; // yyyyMM public static final String THIS_MONTH_TIME = "yyyyMM"; // yyyy public static final String THIS_YEAR_TIME = "yyyy"; // M月d日 HH:mm:ss public static final String WX_NOW_TIME = "M月d日 HH:mm:ss"; public static final String HHMMSS = "HH:mm:ss"; private static final long A_DAY_IN_MILLIS = 1000 * 60 * 60 * 24; private static final Logger logger = LoggerFactory.getLogger(TimeUtil.class); public final static String dateFormat1 = "yyyyMMdd"; public final static String dateFormat2 = "yyyy-MM-dd"; public final static String dateFormat3 = "yyyy/MM/dd"; private static SimpleDateFormat sdf1 = new SimpleDateFormat(dateFormat1); private static SimpleDateFormat sdf2 = new SimpleDateFormat(dateFormat2); private static SimpleDateFormat sdf3 = new SimpleDateFormat(dateFormat3); private static SimpleDateFormat sdf4 = new SimpleDateFormat(NOW_TIME_1); private static SimpleDateFormat sdf5 = new SimpleDateFormat(); public static Calendar getCalendar(long millis) { Calendar calendar = Calendar.getInstance(); calendar.setTime(new Date(millis)); return calendar; } public static Date parse(String format, String date) { try { return new SimpleDateFormat(format).parse(date); } catch (ParseException e) { throw new RuntimeException(e); } } public static String format(String format, Date date) { return new SimpleDateFormat(format).format(date); } /** * 获取当前时间 格式为 yyyy-MM-dd HH:mm:ss * @return */ public static String getCurrentTime() { return format(NOW_TIME_1, new Date()); } /** * 获取当前时间 * @return 返回当前时间格式为yyyyMMddHHmmss的long型,如20151231235900 */ public static long getNowTime() { return Long.parseLong(format(NOW_TIME_2, new Date())); } /** * 获取当前时间 * @return 返回当前时间格式为yyyyMMddHHmmss的long型,如201512312359 */ public static long getNowMinTime() { return Long.parseLong(format(NOW_TIME_3, new Date())); } /** * 获取几个月前时间 * @param mouth 几个月前 主要是负数 如一个月前 则为-1 * @return 返回当前时间格式为yyyyMMddHHmmss的long型,如20151231235900 */ public static long getSomeMonthsAgoTime(int mouth) { Date dNow = new Date(); Calendar calendar = Calendar.getInstance(); calendar.setTime(dNow); calendar.add(Calendar.MONTH, mouth); return Long.parseLong(format(NOW_TIME_2, calendar.getTime())); } /** * 获取当月时间 * @return 返回当前时间格式为yyyyMMddHHmmss的long型,如当天是2017年6月13日11点55分10秒,返回20170600000000 */ public static long getThisMonthsTime() { long thisMonthsTime = Long.parseLong(format(THIS_MONTH_TIME, new Date())); thisMonthsTime *= 100000000l; return thisMonthsTime; } /** * 获取今年开始时间 如果现在是 2018-09-06 19:21:03,那么结果是20180101000000 * @return */ public static long getThisYearStartTime(){ long thisYearTime = Long.parseLong(format(THIS_YEAR_TIME, new Date())); thisYearTime = thisYearTime * 10000000000l + 101000000l; return thisYearTime; } /** * 将时间格式为yyyyMMddHHmmss的long型转为 LocalDateTime,如20151231235923 * @param time * @return */ public static LocalDateTime long2LocalDateTime(long time){ int year = (int)(time / 10000000000l) ; int month = (int)((time - year * 10000000000l) / 100000000l) ; int dayOfMonth = (int)((time - year * 10000000000l - month * 100000000l) / 1000000l) ; int hour = (int)((time - year * 10000000000l - month * 100000000l - dayOfMonth * 1000000l) / 10000l) ; int minute = (int)((time - year * 10000000000l - month * 100000000l - dayOfMonth * 1000000l - hour * 10000l) / 100l) ; int second = (int)(time - year * 10000000000l - month * 100000000l - dayOfMonth * 1000000l - hour * 10000l - minute * 100l) ; return LocalDateTime.of(year, month, dayOfMonth, hour, minute, second); } /** * 从时间格式为yyyyMMddHHmmss的long型中获取小时,如20151231235923返回23 * @param time * @return */ public static int getHourFromTime(long time){ int year = (int)(time / 10000000000l) ; int month = (int)((time - year * 10000000000l) / 100000000l) ; int dayOfMonth = (int)((time - year * 10000000000l - month * 100000000l) / 1000000l) ; return (int)((time - year * 10000000000l - month * 100000000l - dayOfMonth * 1000000l) / 10000l) ; } /** * 获取今年开始时间 如果现在是 2018-09-06 19:21:03,那么结果是20180906000000 * @return */ public static long getThisDayStartTime(){ long thisDayTime = Long.parseLong(format(THIS_DAY_TIME, new Date())); thisDayTime = thisDayTime * 1000000l; return thisDayTime; } /** * 获取指定时间开始时间 如果是 2018-09-06 19:21:03,那么结果是20180906000000 * @return */ public static long getDayStartTime(long time){ long thisDayTime = time / 1000000l; thisDayTime = thisDayTime * 1000000l; return thisDayTime; } /** * 获取当前时间 * @return 返回当前时间格式为M月d日 HH:mm:ss,如5月11日 18:00:00 */ public static String getWxNowTime() { return format(WX_NOW_TIME, new Date()); } /** * 获取将yyyyMMddHHmmss的long型转为M月d日 HH:mm:ss,如5月11日 18:00:00 */ public static String getWxTime(long time) { String timeStr = timeLong2Str(time); timeStr = timeStr.substring(5).replace("-", "月").replace(" ", "日 "); if (timeStr.startsWith("0")) { timeStr = timeStr.substring(1); } timeStr = timeStr.replace("月0", "月"); return timeStr; } /** * 时间转换 将long转为字符串 即将 "20151231235900" 转为 "2015-12-31 23:59:00" * @param time * @return */ public static String timeLong2Str(long time) { if(StringUtil.notEmpty(time)){ String result = ""; StringBuffer datestr=new StringBuffer(String.valueOf(time)); if(datestr.length() == 14){ result=datestr.insert(4, "-").insert(7, "-").insert(10, " ").insert(13, ":").insert(16, ":").toString(); }else if(datestr.length() == 8) { result=datestr.insert(4, "-").insert(7, "-").toString(); } return result; }else { return String.valueOf(time); } } /** * 时间转换 将long转为字符串 即将 "20151231235900" 转为 "20151231" * @param time * @return */ public static String timeLong2yyyyMMddStr(long time) { return String.valueOf(time / 1000000); } public static boolean isValidDate(String str) { if (StringUtils.isEmpty(str)){ return false; } boolean convertSuccess = true; try { synchronized (sdf4){ // 设置lenient为false. // 否则SimpleDateFormat会比较宽松地验证日期,比如2007/02/29会被接受,并转换成2007/03/01 sdf4.setLenient(false); sdf4.parse(str); } } catch (ParseException e) { // e.printStackTrace(); // 如果throw java.text.ParseException或者NullPointerException,就说明格式不对 convertSuccess = false; } return convertSuccess; } public static boolean isValidDate(String str,String pattern) { if (StringUtils.isEmpty(str) || StringUtils.isEmpty(pattern)){ return false; } boolean convertSuccess = true; try { synchronized (sdf5){ // 设置lenient为false. // 否则SimpleDateFormat会比较宽松地验证日期,比如2007/02/29会被接受,并转换成2007/03/01 sdf5.applyPattern(pattern); sdf5.setLenient(false); sdf5.parse(str); } } catch (ParseException e) { // e.printStackTrace(); // 如果throw java.text.ParseException或者NullPointerException,就说明格式不对 convertSuccess = false; } return convertSuccess; } /** * 时间转换 将字符串转为long 即将 "2015-12-31 23:59:00" 转为 "20151231235900" * @return */ public static long timeStr2Long(String timeStr) { if (timeStr == null || timeStr.length() == 0) { return 0; } timeStr = timeStr.replaceAll("-", "").replaceAll(":", "").replaceAll(" ", ""); long time = Long.parseLong(timeStr); return time; } /** * 时间转换 根据不同样式的字符串转为long,即将 "2015-12-31 23:59:00" 转为 "20151231235900" * 且对字符串要求较为严格,类似于 2015-13-01这类的无法转换会返回0 * * @param timeStr 时间字符串 * @param pattern 时间模板 * @return 时间戳数字 * @author wxy */ public static long timeStr2Long(String timeStr, String pattern) { SimpleDateFormat simpleDateFormat = new SimpleDateFormat(pattern); simpleDateFormat.setLenient(false); try { Date parse = simpleDateFormat.parse(timeStr); String format = format(NOW_TIME_2, parse); return Long.parseLong(format); } catch (ParseException e) { return 0; } } /** * 检测时间是否符合要求 * @param time 时间格式是yyyy-MM-dd HH:mm:ss * @return */ public static boolean checkTimeStr(String time) { return CharUtil.characterDetection(time, CharUtil.TIME_LSDF_MATCH); } /** * 检测时间是否符合要求 * @param time 时间格式是yyyyMMddHHmmss * @return */ public static boolean checkTimeData(String time) { return CharUtil.characterDetection(time, CharUtil.TIME_NOWTIMEDF_MATCH); } /** * 判断当前时间是否在一个时间范围内 * @param startTime * @param endTime * @return */ public static boolean isInTimeScope(String startTime, String endTime) { return isInTimeScope(System.currentTimeMillis(), startTime, endTime); } /** * 判断一个时间是否处于一个时间范围内 * @param aTime * @param startTime * @param endTime * @return */ public static boolean isInTimeScope(String aTime, String startTime, String endTime) { return isInTimeScope(parse(NOW_TIME_1, aTime).getTime(), startTime, endTime); } /** * 判断一个时间是否处于一个时间范围内 * 如果不能解析起始或结束时间,则返回false * 如果起始和结束时间一样,则返回false * @param aTime * @param startTime * @param endTime * @return */ public static boolean isInTimeScope(long aTime, String startTime, String endTime) { // 设置给定的时间 Calendar aCalendar = getCalendar(aTime); // 基于当前时间设置开始、结束时间 long currentTimeMillis = System.currentTimeMillis(); Calendar startCalendar = getTimeScope(currentTimeMillis, startTime); Calendar endCalendar = getTimeScope(currentTimeMillis, endTime); if (startCalendar == null || endCalendar == null || startCalendar.compareTo(endCalendar) == 0) { return false; } // 如果开始时间大于结束时间,则证明时间范围处于跨天情况(例:22:00 ~ 08:00),将结束时间前进一天 if (startCalendar.compareTo(endCalendar) > 0) { endCalendar = getCalendar(endCalendar.getTimeInMillis() + A_DAY_IN_MILLIS); } // startCalendar <= aCalendar <= endCalendar return aCalendar.compareTo(startCalendar) >= 0 && aCalendar.compareTo(endCalendar) <= 0; } /** * 基于一个时间戳和时间段构造一个时间 * @param timestamp * @param timeScope * @return */ private static Calendar getTimeScope(long timestamp, String timeScope) { Date scopeDate = null; try { scopeDate = parse(HHMMSS, timeScope); } catch (Throwable e) { logger.error("parse timeScope[{}] error", timeScope, e); } if (scopeDate == null) { return null; } Calendar stampCal = getCalendar(timestamp); Calendar scopeCal = getCalendar(scopeDate.getTime()); stampCal.set(HOUR_OF_DAY, scopeCal.get(HOUR_OF_DAY)); stampCal.set(MINUTE, scopeCal.get(MINUTE)); stampCal.set(SECOND, scopeCal.get(SECOND)); stampCal.set(MILLISECOND, scopeCal.get(MILLISECOND)); return stampCal; } public static String validDate(String date) { String ret = "-1"; Date date1 = null; int format1 = 1; int format2 = 1; int format3 = 1; if (!StringUtils.isEmpty(date)){ if ("长期".equals(date.trim())){ ret ="0"; // 0 表示长期 return ret; } if(date.length()==6||((date.contains("-")||date.contains("/"))&&date.length()==8)){ ret = "-1"; // 不合法 return ret; } if(date.indexOf("-")>0&&date.indexOf("/")>0){ ret = "-1"; // 不合法 }else if (date.indexOf("-")>0&&date.indexOf("/")<0){ try { synchronized (sdf2){ date1 = sdf2.parse(date); } } catch (ParseException e) { format2 = 0; } }else if (date.indexOf("-")<0&&date.indexOf("/")>0){ try { synchronized (sdf3){ date1 = sdf3.parse(date); } } catch (ParseException e) { format3 = 0; } }else{ try { synchronized (sdf1){ date1 = sdf1.parse(date); } } catch (ParseException e) { format3 = 0; } } }else{ ret = "19700101"; } if (format1==0&&format2==0&&format3==0){ ret = "-1"; // 不合法 } if(date1!=null){ synchronized (sdf1) { ret = sdf1.format(date1); } } return ret; } public static void test_isInTimeScope() { // <下临界值 System.out.println(isInTimeScope("2018-01-26 02:28:22", "02:28:23", "10:28:23")); System.out.println(isInTimeScope("2018-01-26 10:28:22", "10:28:23", "15:28:23")); System.out.println(isInTimeScope("2018-01-26 15:28:22", "15:28:23", "22:28:23")); System.out.println(isInTimeScope("2018-01-26 22:28:22", "22:28:23", "08:28:23")); System.out.println(isInTimeScope("2018-01-26 22:28:22", "22:28:23", "15:28:23")); System.out.println("-------------------------------false------------------------------------------"); // =下临界值 System.out.println(isInTimeScope("2018-01-26 02:28:23", "02:28:23", "10:28:23")); System.out.println(isInTimeScope("2018-01-26 10:28:23", "10:28:23", "15:28:23")); System.out.println(isInTimeScope("2018-01-26 15:28:23", "15:28:23", "22:28:23")); System.out.println(isInTimeScope("2018-01-26 22:28:23", "22:28:23", "08:28:23")); System.out.println(isInTimeScope("2018-01-26 22:28:23", "22:28:23", "15:28:23")); System.out.println("-------------------------------true------------------------------------------"); // <上临界值 System.out.println(isInTimeScope("2018-01-26 03:28:23", "02:28:23", "10:28:23")); System.out.println(isInTimeScope("2018-01-26 11:28:23", "10:28:23", "15:28:23")); System.out.println(isInTimeScope("2018-01-26 21:28:23", "15:28:23", "22:28:23")); System.out.println(isInTimeScope("2018-01-27 07:28:23", "22:28:23", "08:28:23")); System.out.println(isInTimeScope("2018-01-27 10:28:23", "22:28:23", "15:28:23")); System.out.println("-------------------------------true------------------------------------------"); // =上临界值 System.out.println(isInTimeScope("2018-01-26 10:28:23", "02:28:23", "10:28:23")); System.out.println(isInTimeScope("2018-01-26 15:28:23", "10:28:23", "15:28:23")); System.out.println(isInTimeScope("2018-01-26 22:28:23", "15:28:23", "22:28:23")); System.out.println(isInTimeScope("2018-01-27 08:28:23", "22:28:23", "08:28:23")); System.out.println(isInTimeScope("2018-01-27 15:28:23", "22:28:23", "15:28:23")); System.out.println("-------------------------------true------------------------------------------"); // >上临界值 System.out.println(isInTimeScope("2018-01-26 10:28:24", "02:28:23", "10:28:23")); System.out.println(isInTimeScope("2018-01-26 15:28:24", "10:28:23", "15:28:23")); System.out.println(isInTimeScope("2018-01-26 22:28:24", "15:28:23", "22:28:23")); System.out.println(isInTimeScope("2018-01-27 08:28:24", "22:28:23", "08:28:23")); System.out.println(isInTimeScope("2018-01-27 15:28:24", "22:28:23", "15:28:23")); System.out.println("-------------------------------false------------------------------------------"); } }