private static final ThreadLocal sdf = ThreadLocal.withInitial(
() -> new SimpleDateFormat("yyyy-MM-dd")
);
这种办法使用简单,但是不灵活,如果有多种格式化的要求,则需要建很多对象,而且当线程没有合理控制,不断死亡和增加,大量的threadLocal会增加gc负担
public class DateFormatUtilsTest {
@org.junit.Test
public void format() throws Exception {
System.out.println(DateFormatUtils.format(new Date(),"yyyy-MM-dd"));
System.out.println(DateFormatUtils.format(new Date(),"HH:mm:ss"));
System.out.println(DateFormatUtils.format(new Date(),"MM月月dd日日ss秒秒"));
}
@org.junit.Test
public void parse() throws Exception {
System.out.println(DateFormatUtils.parse("16:20","HH:mm"));
System.out.println(DateFormatUtils.parse("2016年12月","yyyy年MM月"));
System.out.println(DateFormatUtils.parse("10-20","MM-dd"));
System.out.println(DateFormatUtils.parse("2014-09-06 11:53:50","yyyy-MM-dd HH:mm:ss"));
}
}
package com.fly.design.utils;
import java.util.Calendar;
import java.util.Date;
import java.util.Map;
import java.util.Objects;
import java.util.function.BiConsumer;
import java.util.function.Function;
/**
* @author weijun.zou
* Create on 2018/3/7
*/
public class DateFormatUtils {
private static Map>> parseMapper = Map.of(
2, Map.of(
'M', (calendar, string) -> calendar.set(Calendar.MONTH, Integer.valueOf(string) - 1),
'd', (calendar, string) -> calendar.set(Calendar.DAY_OF_MONTH, Integer.valueOf(string)),
'H', (calendar, string) -> calendar.set(Calendar.HOUR_OF_DAY, Integer.valueOf(string)),
'h', (calendar, string) -> calendar.set(Calendar.HOUR, Integer.valueOf(string)),
'm', (calendar, string) -> calendar.set(Calendar.MINUTE, Integer.valueOf(string)),
's', (calendar, string) -> calendar.set(Calendar.SECOND, Integer.valueOf(string))
),
4, Map.of(
'y', (calendar, string) -> calendar.set(Calendar.YEAR, Integer.valueOf(string))
)
);
private static Map>> formatMapper = Map.of(
2, Map.of(
'M', calendar -> String.format("%02d", calendar.get(Calendar.MONTH) + 1),
'd', calendar -> String.format("%02d", calendar.get(Calendar.DAY_OF_MONTH)),
'H', calendar -> String.format("%02d", calendar.get(Calendar.HOUR_OF_DAY)),
'h', calendar -> String.format("%02d", calendar.get(Calendar.HOUR)),
'm', calendar -> String.format("%02d", calendar.get(Calendar.MINUTE)),
's', calendar -> String.format("%02d", calendar.get(Calendar.SECOND))
),
4, Map.of(
'y', calendar -> String.format("%04d", calendar.get(Calendar.YEAR))
)
);
/**
* 将时间按照格式转字符串
* format格式
* yyyy: 年
* MM: 月
* dd: 日
* HH: 时
* mm: 分
* ss: 秒
*/
public static String format(Date date, String format) {
Objects.requireNonNull(date);
Objects.requireNonNull(format);
Calendar calendar = Calendar.getInstance();
calendar.setTime(date);
char[] chars = format.toCharArray();
for (int i = 0; i < chars.length; ) {
int overlap = overlap(chars, i);
if (formatMapper.getOrDefault(overlap, Map.of()).containsKey(chars[i])) {
String value = formatMapper.get(overlap).get(chars[i]).apply(calendar);
replace(chars, value.toCharArray(), i);
}
i += overlap;
}
return new String(chars);
}
public static Date parse(String dateString, String format) {
return modify(new Date(), dateString, format);
}
public static Date modify(Date date, String dateString, String format) {
Objects.requireNonNull(date);
Objects.requireNonNull(dateString);
Objects.requireNonNull(format);
if (dateString.length() != format.length()) {
throw new IllegalArgumentException(dateString);
}
Calendar calendar = Calendar.getInstance();
calendar.setTime(date);
char[] chars = format.toCharArray();
for (int index = 0; index < chars.length; ) {
int overlap = overlap(chars, index);
if (parseMapper.containsKey(overlap) && parseMapper.get(overlap).containsKey(chars[index])) {
parseMapper.get(overlap).get(chars[index])
.accept(calendar, dateString.substring(index, index + overlap));
}
index += overlap;
}
return calendar.getTime();
}
private static int overlap(char[] chars, int index) {
char c = chars[index];
int number = 0;
while (index < chars.length && chars[index++] == c) {
number++;
}
return number;
}
private static void replace(char[] target, char[] copy, int index) {
for (int i = 0; index < target.length && i < copy.length; index++, i++) {
target[index] = copy[i];
}
}
}