Java工作中 经常用到的工具类Util(持续更新)

news2024/11/27 19:57:07


前言

   Java本身自带了许多非常好用的工具类,但有时我们的业务千奇百怪,自带的工具类又无法满足业务需求,需要在这些工具类的基础上进行二次封装改造。以下就是作者在实际工作中,积累总结的一些Util


一、时间相关

package com.test.java.util;

import com.google.common.collect.Lists;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.time.DateFormatUtils;
import org.apache.commons.lang3.time.DateUtils;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.time.Instant;
import java.time.LocalDateTime;
import java.time.LocalTime;
import java.time.ZoneId;
import java.time.format.DateTimeFormatter;
import java.util.*;

/**
 * 时间工具类
 */
@Slf4j
public class DateUtil {

    /*** 常用的时间模型常量*/
    public static final String PATTERN_DATE_TIME_MONTH = "yyyy-MM-dd";
    private static final String PATTERN_DATE_TIME = "yyyy-MM-dd HH:mm:ss";
    public static final String PATTERN_DATE_TIME_MILLISECOND = "yyyy-MM-dd HH:mm:ss.SSS";
    private static final String EXPORT_FORMAT_DATE_TIME = "yyyyMMdd-hhmmss";

    /*** 周末*/
    public static List<Integer> holidays = Lists.newArrayList(6, 7);
    /*** 工作日*/
    public static List<Integer> workdays = Lists.newArrayList(1, 2, 3, 4, 5);

    /**
     * 获取指定的format,每次重建避免线程安全问题 yyyy-MM-dd HH:mm:ss
     */
    public static SimpleDateFormat getYyyyMmDdHhMmSs() {
        return new SimpleDateFormat(PATTERN_DATE_TIME);
    }

    /**
     * LocalDateTime转为String,格式为:"2023-10-13 15:40:23"
     */
    public static String formatDateTime(LocalDateTime dateTime) {
        if (Objects.isNull(dateTime)) {
            return "";
        }
        DateTimeFormatter formatter = DateTimeFormatter.ofPattern(PATTERN_DATE_TIME);
        return dateTime.format(formatter);
    }

    /**
     * LocalDateTime转为String,格式为:"2023-10-13"
     */
    public static String formatDateTimeOfMonth(LocalDateTime dateTime) {
        if (Objects.isNull(dateTime)) {
            return "";
        }
        DateTimeFormatter formatter = DateTimeFormatter.ofPattern(PATTERN_DATE_TIME_MONTH);
        return dateTime.format(formatter);
    }

    /**
     * LocalDateTime转为Date
     */
    public static Date localDateTimeToDate(LocalDateTime localDateTime) {
        return Date.from(localDateTime.atZone(ZoneId.systemDefault()).toInstant());
    }

    /**
     * LocalDateTime转为时间戳
     */
    public static String dateTimestamp(LocalDateTime date) {
        return DateTimeFormatter.ofPattern("yyMMddHHmmssSSS").format(date);
    }

    /**
     * LocalDateTime转为String,自定义时间格式
     *
     * @param dateTime LocalDateTime类型的时间
     * @param pattern  自定义的时间格式
     */
    public static String formatDateTime(LocalDateTime dateTime, String pattern) {
        if (Objects.isNull(dateTime)) {
            return "";
        }
        DateTimeFormatter formatter = DateTimeFormatter.ofPattern(pattern);
        return dateTime.format(formatter);
    }

    /**
     * Date转为String,格式为:“2023-01-01”
     */
    public static String formatDateTime(Date dateTime) {
        if (Objects.nonNull(dateTime)) {
            return DateFormatUtils.format(dateTime, PATTERN_DATE_TIME_MONTH);
        }
        return "";
    }

    /**
     * Date转为String,格式为:“2023-01-01 12:10:50”
     */
    public static String formatDateOfDate(Date dateTime) {
        if (Objects.nonNull(dateTime)) {
            return DateFormatUtils.format(dateTime, PATTERN_DATE_TIME);
        }
        return "";
    }

    /**
     * Date转为String,格式为:“20230101-121050”
     */
    public static String exportFormatDateTime(Date dateTime) {
        if (Objects.nonNull(dateTime)) {
            return DateFormatUtils.format(dateTime, EXPORT_FORMAT_DATE_TIME);
        }
        return "";
    }

    /**
     * Date转为String,格式为:“2023.01.01”
     */
    public static String formatDate(Date dateTime) {
        if (Objects.nonNull(dateTime)) {
            return DateFormatUtils.format(dateTime, "yyyy.MM.dd");
        }
        return "";
    }

    /**
     * Date转为String时间,自定义时间格式
     *
     * @param dateTime Date时间
     * @param pattern  自定义的时间格式
     */
    public static String formatDateTime(Date dateTime, String pattern) {
        if (Objects.nonNull(dateTime)) {
            return DateFormatUtils.format(dateTime, pattern);
        }
        return "";
    }

    /**
     * 字符串时间转为Date,格式为:"Sun Oct 01 00:00:00 CST 2023"
     */
    public static Date strToDateTimeOfMonth(String strDate) {
        try {
            strDate = strDate.substring(0, 10);
            return DateUtils.parseDate(strDate, PATTERN_DATE_TIME_MONTH);
        } catch (ParseException e) {
            log.error("时间转换异常:{}", e.getMessage());
            throw new RuntimeException(e);
        }
    }

    /**
     * 字符串时间转为Date,格式为:"Sun Oct 01 02:56:20 CST 2023"
     */
    public static Date strToDateTime(String strDate) {
        if (strDate.length() != 19) {
            throw new RuntimeException("入参时间格式不正确");
        }
        try {

            return DateUtils.parseDate(strDate, PATTERN_DATE_TIME);
        } catch (ParseException e) {
            log.error("时间转换异常:{}", e.getMessage());
            throw new RuntimeException(e);
        }
    }

    /**
     * 将Date对象转化为指定格式dateFormat的字符串
     *
     * @return String
     */
    public static String getDate(Date date, String dateFormat) {
        SimpleDateFormat format = new SimpleDateFormat(dateFormat);
        return format.format(date);
    }

    /**
     * 将指定格式fromFormat的Date字符串转化为Date对象
     */
    public static Date getDate(String date) {
        SimpleDateFormat sdf = getYyyyMmDdHhMmSs();
        try {
            return sdf.parse(date);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    /**
     * 将指定格式fromFormat的Date字符串转化为Date对象
     *
     * @return Date
     */
    public static Date getDate(String date, String fromFormat) {
        try {
            SimpleDateFormat fromSimpleDateFormat = new SimpleDateFormat(fromFormat);
            return fromSimpleDateFormat.parse(date);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    /**
     * 字符串时间转为LocalDateTime,格式为:"2023-10-01T02:56:20"
     */
    public static LocalDateTime strToLocalDateTime(String strDate) {
        if (strDate.length() != 19) {
            throw new RuntimeException("入参时间格式不正确");
        }
        try {
            Date date = DateUtils.parseDate(strDate, "yyyy-MM-dd HH:mm:ss");
            return date.toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime();
        } catch (ParseException e) {
            log.error("时间转换异常:{}", e.getMessage());
            throw new RuntimeException(e);
        }
    }

    /**
     * 字符串时间转为LocalDateTime,格式为:"2023-10-01T02:56:20.001"
     */
    public static LocalDateTime strToLocalDateTimeMillisecond(String strDate) {
        try {
            if (strDate.length() != 23) {
                throw new RuntimeException("入参时间格式不正确");
            }
            Date date = DateUtils.parseDate(strDate, PATTERN_DATE_TIME_MILLISECOND);
            return date.toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime();
        } catch (ParseException e) {
            log.error("时间转换异常:{}", e.getMessage());
            throw new RuntimeException(e);
        }
    }

    /**
     * 计算两个时间差
     */
    public static String getDatePoor(Date endDate, Date nowDate) {
        long nd = 1000 * 24 * 60 * 60;
        long nh = 1000 * 60 * 60;
        long nm = 1000 * 60;
        // long ns = 1000;
        // 获得两个时间的毫秒时间差异
        long diff = Math.abs(endDate.getTime() - nowDate.getTime());
        // 计算差多少天
        long day = diff / nd;
        // 计算差多少小时
        long hour = diff % nd / nh;
        // 计算差多少分钟
        long min = diff % nd % nh / nm;
        // 计算差多少秒//输出结果
        // long sec = diff % nd % nh % nm / ns;
        return day + "天" + hour + "小时" + min + "分钟";
    }

    /**
     * 计算两个时间相差天数
     */
    public static int differentDaysByMillisecond(Date date1, Date date2) {
        return Math.abs((int) ((date2.getTime() - date1.getTime()) / (1000 * 3600 * 24)));
    }

    /**
     * 计算两个时间相差小时
     */
    public static int differentHourByMillisecond(Date date1, Date date2) {
        return Math.abs((int) ((date2.getTime() - date1.getTime()) / (1000 * 3600)));
    }

    /**
     * 计算两个时间相差分钟
     */
    public static int differentMinByMillisecond(Date date1, Date date2) {
        return Math.abs((int) ((date2.getTime() - date1.getTime()) / (1000 * 60)));
    }

    /**
     * 获得某天最大时间,例如:Wed Nov 29 23:59:59 CST 2023
     */
    public static Date getEndOfDay(Date date) {
        LocalDateTime localDateTime = LocalDateTime.ofInstant(Instant.ofEpochMilli(date.getTime()), ZoneId.systemDefault());
        LocalDateTime endOfDay = localDateTime.with(LocalTime.MAX);
        return Date.from(endOfDay.atZone(ZoneId.systemDefault()).toInstant());
    }

    /**
     * 获得某天最小时间,例如:Wed Nov 29 00:00:00 CST 2023
     */
    public static Date getStartOfDay(Date date) {
        LocalDateTime localDateTime = LocalDateTime.ofInstant(Instant.ofEpochMilli(date.getTime()), ZoneId.systemDefault());
        LocalDateTime startOfDay = localDateTime.with(LocalTime.MIN);
        return Date.from(startOfDay.atZone(ZoneId.systemDefault()).toInstant());
    }

    /**
     * 获取相对于date前后的某一天
     */
    public static Date anotherDay(Date date, int i) {
        Calendar cal = Calendar.getInstance();
        cal.setTime(date);
        cal.add(Calendar.DATE, i);
        return cal.getTime();
    }

    /**
     * 给定值向后加月份
     */
    public static Date stepMonth(Date sourceDate, int month) {
        Calendar c = Calendar.getInstance();
        c.setTime(sourceDate);
        c.add(Calendar.MONTH, month);
        return c.getTime();
    }

    /**
     * 给定值向后加年份
     */
    public static Date stepYear(Date sourceDate, int year) {
        Calendar c = Calendar.getInstance();
        c.setTime(sourceDate);
        c.add(Calendar.YEAR, year);
        return c.getTime();
    }

    /**
     * 该年最后一天的 时、分、秒以23:59:59结尾
     */
    public static Date dateTimeYearEndWidth(Date dateTime) {
        String dateTimeString = getDate(dateTime, PATTERN_DATE_TIME);
        return getDate(dateTimeString.substring(0, 4) + "-12-31 23:59:59");
    }

    /**
     * 获取过去N天内的日期数组(不包含今天)返回的时间类型为:yyyy-MM-dd
     */
    public static ArrayList<String> getLastDays(int intervals) {
        ArrayList<String> pastDaysList = new ArrayList<>();
        for (int i = intervals; i > 0; i--) {
            Calendar calendar = Calendar.getInstance();
            calendar.set(Calendar.DAY_OF_YEAR, calendar.get(Calendar.DAY_OF_YEAR) - i);
            Date today = calendar.getTime();
            SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd");
            pastDaysList.add(format.format(today));
        }
        return pastDaysList;
    }

}

附上测试demo:

  public static void main(String[] args) {

        LocalDateTime nowDate = LocalDateTime.now();
        Date date = new Date();

        String a = DateUtil.formatDateTime(nowDate);
        System.out.println("LocalDateTime转为String时间(带时分秒):" + a);

        String b = DateUtil.formatDateTimeOfMonth(nowDate);
        System.out.println("LocalDateTime转为String时间(不带时分秒):" + b);

        String c = DateUtil.dateTimestamp(nowDate);
        System.out.println("LocalDateTime转为时间戳:" + c);

        String d = DateUtil.formatDateTime(nowDate, "yyyy-MM-dd ");
        System.out.println("LocalDateTime转为String时间(自定义格式):" + d);

        Date dt = DateUtil.localDateTimeToDate(nowDate);
        System.out.println("LocalDateTime转为Date:" + dt);

        String s = DateUtil.formatDateTime(date);
        System.out.println("Date转为String时间(不带时分秒):" + s);

        String s1 = DateUtil.formatDateOfDate(date);
        System.out.println("Date转为String时间(带时分秒):" + s1);

        String s2 = DateUtil.exportFormatDateTime(date);
        System.out.println("Date转为String时间(导出模式):" + s2);

        String s3 = DateUtil.formatDate(date);
        System.out.println("Date转为String时间(特殊模式):" + s3);

        String s4 = DateUtil.formatDateTime(date, "yyyy-MM-dd");
        System.out.println("Date转为String时间(自定义格式):" + s4);

        Date date1 = DateUtil.strToDateTimeOfMonth("2023-10-01 02:56:20");
        System.out.println("字符串时间转为Date(不带时分秒)" + date1);

        Date date2 = DateUtil.strToDateTime("2023-10-01 02:56:20");
        System.out.println("字符串时间转为Date(带时分秒)" + date2);

        LocalDateTime ld = DateUtil.strToLocalDateTime("2023-10-01 02:56:20");
        System.out.println("字符串时间转为LocalDateTime(带时分秒):" + ld);

        LocalDateTime ld2 = DateUtil.strToLocalDateTimeMillisecond("2023-10-01 02:56:20.001");
        System.out.println("字符串时间转为LocalDateTime(带毫秒)" + ld2);

        String str1 = "2023-11-25 08:00:00";
        String str2 = "2023-11-29 00:00:00";
        Date date3 = DateUtil.strToDateTime(str1);
        Date date4 = DateUtil.strToDateTime(str2);
        String datePoor = DateUtil.getDatePoor(date3, date4);
        System.out.println("两时间相差:" + datePoor);

        int i = DateUtil.differentDaysByMillisecond(date3, date4);
        System.out.println("两时间相差:" + i + "天");

        int i2 = DateUtil.differentHourByMillisecond(date3, date4);
        System.out.println("两时间相差:" + i2 + "小时");

        int i3 = DateUtil.differentMinByMillisecond(date3, date4);
        System.out.println("两时间相差:" + i3 + "分钟");

        Date endOfDay = DateUtil.getEndOfDay(date);
        System.out.println("某天最大时间:" + endOfDay);

        Date startOfDay = DateUtil.getStartOfDay(date);
        System.out.println("某天最小时间:" + startOfDay);

        Date date5 = DateUtil.anotherDay(date, 1);
        System.out.println("昨天的时间:" + date5);

        Date date6 = DateUtil.stepMonth(date, 1);
        System.out.println("下个月的时间:" + date6);

        Date date7 = DateUtil.stepYear(date, 1);
        System.out.println("明年的时间:" + date7);

        Date date8 = DateUtil.dateTimeYearEndWidth(date);
        System.out.println("本年最后一天的时间:" + date8);

        ArrayList<String> lastDays = DateUtil.getLastDays(7);
        System.out.println("过去7天内的日期:" + lastDays);

    }

 结果:

二、正则校验

package com.test.java.util;

import java.util.ArrayList;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * 正则相关工具类
 */
public class ValidateUtil {

    /*** 手机号(简单),以1开头的11位纯数字*/
    public static final String REGEX_MOBILE_SIMPLE = "^[1]\\d{10}$";

    /**
     * 手机号(精确)
     * <p>移动:134(0-8)、135、136、137、138、139、147、150、151、152、157、158、159、178、182、183、184、187、188</p>
     * <p>联通:130、131、132、145、155、156、175、176、185、186</p>
     * <p>电信:133、153、173、177、180、181、189</p>
     * <p>全球星:1349</p>
     * <p>虚拟运营商:170</p>
     */
    public static final String REGEX_MOBILE_EXACT = "^((13[0-9])|(14[5,7])|(15[0-3,5-9])|(17[0,3,5-8])|(18[0-9])|(147))\\d{8}$";

    /*** 固定电话号码*/
    public static final String REGEX_TEL = "^0\\d{2,3}[- ]?\\d{7,8}";

    /*** 身份证号(15位身份证号)*/
    public static final String REGEX_ID_CARD15 = "^[1-9]\\d{7}((0\\d)|(1[0-2]))(([0|1|2]\\d)|3[0-1])\\d{3}$";

    /*** 身份证号(18位身份证号)*/
    public static final String REGEX_ID_CARD18 = "^[1-9]\\d{5}[1-9]\\d{3}((0\\d)|(1[0-2]))(([0|1|2]\\d)|3[0-1])\\d{3}([0-9Xx])$";

    /*** 身份证号(15和18位)*/
    public static final String REGEX_ID_CARD15AND18 = "(^\\d{8}(0\\d|10|11|12)([0-2]\\d|30|31)\\d{3}$)|(^\\d{6}(18|19|20)\\d{2}(0\\d|10|11|12)([0-2]\\d|30|31)\\d{3}(\\d|X|x)$)";

    /*** 邮箱*/
    public static final String REGEX_EMAIL = "^\\w+([-+.]\\w+)*@\\w+([-.]\\w+)*\\.\\w+([-.]\\w+)*$";

    /*** 网址URL*/
    public static final String REGEX_URL = "[a-zA-z]+://[^\\s]*";

    /*** 汉字*/
    public static final String REGEX_ZH = "^[\\u4e00-\\u9fa5]+$";

    /*** 用户名(取值范围为a-z,A-Z,0-9,"_",汉字,不能以"_"结尾,用户名必须是6-20位)*/
    public static final String REGEX_USERNAME = "^[\\w\\u4e00-\\u9fa5]{6,20}(?<!_)$";

    /*** yyyy-MM-dd格式的日期校验,已考虑平闰年*/
    public static final String REGEX_DATE = "^(?:(?!0000)[0-9]{4}-(?:(?:0[1-9]|1[0-2])-(?:0[1-9]|1[0-9]|2[0-8])|(?:0[13-9]|1[0-2])-(?:29|30)|(?:0[13578]|1[02])-31)|(?:[0-9]{2}(?:0[48]|[2468][048]|[13579][26])|(?:0[48]|[2468][048]|[13579][26])00)-02-29)$";

    /*** IP地址*/
    public static final String REGEX_IP = "((2[0-4]\\d|25[0-5]|[01]?\\d\\d?)\\.){3}(2[0-4]\\d|25[0-5]|[01]?\\d\\d?)";

    /*** 双字节字符(包括汉字在内)*/
    public static final String REGEX_DOUBLE_BYTE_CHAR = "[^\\x00-\\xff]";

    /*** 空白行*/
    public static final String REGEX_BLANK_LINE = "\\n\\s*\\r";

    /*** QQ号*/
    public static final String REGEX_TENCENT_NUM = "[1-9][0-9]{4,}";

    /*** 中国邮政编码*/
    public static final String REGEX_ZIP_CODE = "[1-9]\\d{5}(?!\\d)";

    /*** 正整数*/
    public static final String REGEX_POSITIVE_INTEGER = "^[1-9]\\d*$";

    /*** 负整数*/
    public static final String REGEX_NEGATIVE_INTEGER = "^-[1-9]\\d*$";

    /*** 整数*/
    public static final String REGEX_INTEGER = "^-?[1-9]\\d*$";

    /*** 非负整数(正整数 + 0)*/
    public static final String REGEX_NOT_NEGATIVE_INTEGER = "^[1-9]\\d*|0$";

    /*** 非正整数(负整数 + 0)*/
    public static final String REGEX_NOT_POSITIVE_INTEGER = "^-[1-9]\\d*|0$";

    /*** 正浮点数*/
    public static final String REGEX_POSITIVE_FLOAT = "^[1-9]\\d*\\.\\d*|0\\.\\d*[1-9]\\d*$";

    /*** 负浮点数*/
    public static final String REGEX_NEGATIVE_FLOAT = "^-[1-9]\\d*\\.\\d*|-0\\.\\d*[1-9]\\d*$";

    /**
     * 验证手机号(简单)
     *
     * @param input 待验证文本
     * @return true: 匹配 <br> false: 不匹配
     */
    public static boolean isMobileSimple(CharSequence input) {
        return isMatch(REGEX_MOBILE_SIMPLE, input);
    }

    /**
     * 验证手机号(精确)
     *
     * @param input 待验证文本
     * @return true: 匹配 <br> false: 不匹配
     */
    public static boolean isMobileExact(CharSequence input) {
        return isMatch(REGEX_MOBILE_EXACT, input);
    }

    /**
     * 验证固定电话号码
     *
     * @param input 待验证文本
     * @return true: 匹配 <br> false: 不匹配
     */
    public static boolean isTel(CharSequence input) {
        return isMatch(REGEX_TEL, input);
    }

    /**
     * 验证身份证号码(15位)
     *
     * @param input 待验证文本
     * @return true: 匹配 <br> false: 不匹配
     */
    public static boolean isIdCard15(CharSequence input) {
        return isMatch(REGEX_ID_CARD15, input);
    }

    /**
     * 验证身份证号码(18位)
     *
     * @param input 待验证文本
     * @return true: 匹配 <br> false: 不匹配
     */
    public static boolean isIdCard18(CharSequence input) {
        return isMatch(REGEX_ID_CARD18, input);
    }

    /**
     * 验证身份证号码(15/18位)
     *
     * @param input 待验证文本
     * @return true: 匹配 <br> false: 不匹配
     */
    public static boolean isIdCard15and18(CharSequence input) {
        return isMatch(REGEX_ID_CARD15AND18, input);
    }

    /**
     * 验证邮箱
     *
     * @param input 待验证文本
     * @return true: 匹配 <br> false: 不匹配
     */
    public static boolean isEmail(CharSequence input) {
        return isMatch(REGEX_EMAIL, input);
    }

    /**
     * 验证网址URL
     *
     * @param input 待验证文本
     * @return true: 匹配 <br> false: 不匹配
     */
    public static boolean isUrl(CharSequence input) {
        return isMatch(REGEX_URL, input);
    }

    /**
     * 验证汉字
     *
     * @param input 待验证文本
     * @return true: 匹配 <br> false: 不匹配
     */
    public static boolean isZh(CharSequence input) {
        return isMatch(REGEX_ZH, input);
    }

    /**
     * 验证用户名(取值范围为a-z,A-Z,0-9,"_",汉字,不能以"_"结尾,用户名必须是6-20位)
     *
     * @param input 待验证文本
     * @return true: 匹配 <br> false: 不匹配
     */
    public static boolean isUsername(CharSequence input) {
        return isMatch(REGEX_USERNAME, input);
    }

    /**
     * 验证yyyy-MM-dd格式的日期校验,已考虑平闰年
     *
     * @param input 待验证文本
     * @return true: 匹配 <br> false: 不匹配
     */
    public static boolean isDate(CharSequence input) {
        return isMatch(REGEX_DATE, input);
    }

    /**
     * 验证IP地址
     *
     * @param input 待验证文本
     * @return true: 匹配 <br> false: 不匹配
     */
    public static boolean isIp(CharSequence input) {
        return isMatch(REGEX_IP, input);
    }

    /**
     * 判断是否匹配正则
     *
     * @param regex 正则表达式
     * @param input 要匹配的字符串
     * @return true: 匹配 <br> false: 不匹配
     */
    public static boolean isMatch(String regex, CharSequence input) {
        return input != null && input.length() > 0 && Pattern.matches(regex, input);
    }

    /**
     * 获取正则匹配的部分
     *
     * @param regex 正则表达式
     * @param input 要匹配的字符串
     * @return 正则匹配的部分
     */
    public static List<String> getMatches(String regex, CharSequence input) {
        if (input == null) {
            return null;
        }
        List<String> matches = new ArrayList<>();
        Pattern pattern = Pattern.compile(regex);
        Matcher matcher = pattern.matcher(input);
        while (matcher.find()) {
            matches.add(matcher.group());
        }
        return matches;
    }

    /**
     * 获取正则匹配分组
     *
     * @param input 要分组的字符串
     * @param regex 正则表达式
     * @return 正则匹配分组
     */
    public static String[] getSplits(String input, String regex) {
        if (input == null) {
            return null;
        }
        return input.split(regex);
    }

    /**
     * 替换正则匹配的第一部分
     *
     * @param input       要替换的字符串
     * @param regex       正则表达式
     * @param replacement 代替者
     * @return 替换正则匹配的第一部分
     */
    public static String getReplaceFirst(String input, String regex, String replacement) {
        if (input == null) {
            return null;
        }
        return Pattern.compile(regex).matcher(input).replaceFirst(replacement);
    }

    /**
     * 替换所有正则匹配的部分
     *
     * @param input       要替换的字符串
     * @param regex       正则表达式
     * @param replacement 代替者
     * @return 替换所有正则匹配的部分
     */
    public static String getReplaceAll(String input, String regex, String replacement) {
        if (input == null) {
            return null;
        }
        return Pattern.compile(regex).matcher(input).replaceAll(replacement);
    }

}

三、水印相关

        相关的添加水印的代码,在我之前写过的文章里有详细的介绍,感兴趣的同学可以去看看。附上链接:Java实现添加文字水印、图片水印

package com.test.java.util;

import org.apache.commons.lang3.StringUtils;

import javax.imageio.ImageIO;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.net.URL;

/**
 * 水印相关util
 */
public class WatermarkUtil {

    /**
     * 读取本地图片
     *
     * @param path 本地图片存放路径
     */
    public static Image readLocalPicture(String path) {
        if (null == path) {
            throw new RuntimeException("本地图片路径不能为空");
        }
        // 读取原图片信息 得到文件
        File srcImgFile = new File(path);
        try {
            // 将文件对象转化为图片对象
            return ImageIO.read(srcImgFile);
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

    /**
     * 读取网络图片
     *
     * @param path 网络图片地址
     */
    public static Image readNetworkPicture(String path) {
        if (null == path) {
            throw new RuntimeException("网络图片路径不能为空");
        }
        try {
            // 创建一个URL对象,获取网络图片的地址信息
            URL url = new URL(path);
            // 将URL对象输入流转化为图片对象 (url.openStream()方法,获得一个输入流)
            BufferedImage bugImg = ImageIO.read(url.openStream());
            if (null == bugImg) {
                throw new RuntimeException("网络图片地址不正确");
            }
            return bugImg;
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

    /**
     * 水印处理
     *
     * @param image     图片对象
     * @param type      水印类型(1-文字水印 2-图片水印)
     * @param watermark 水印内容(文字水印内容/图片水印的存放路径)
     */
    public static String manageWatermark(Image image, Integer type, String watermark) {
        int imgWidth = image.getWidth(null);
        int imgHeight = image.getHeight(null);
        BufferedImage bufImg = new BufferedImage(imgWidth, imgHeight, BufferedImage.TYPE_INT_RGB);
        // 加水印:
        // 创建画笔
        Graphics2D graphics = bufImg.createGraphics();
        // 绘制原始图片
        graphics.drawImage(image, 0, 0, imgWidth, imgHeight, null);

        // 校验水印的类型
        if (type == 1) {
            if (StringUtils.isEmpty(watermark)) {
                throw new RuntimeException("文字水印内容不能为空");
            }
            // 添加文字水印:
            // 根据图片的背景设置水印颜色
            graphics.setColor(new Color(255, 255, 255, 128));
            // 设置字体  画笔字体样式为微软雅黑,加粗,文字大小为45pt
            graphics.setFont(new Font("微软雅黑", Font.BOLD, 45));
            // 设置水印的坐标(为原图片中间位置)
            int x = (imgWidth - getWatermarkLength(watermark, graphics)) / 2;
            int y = imgHeight / 2;
            // 画出水印 第一个参数是水印内容,第二个参数是x轴坐标,第三个参数是y轴坐标
            graphics.drawString(watermark, x, y);
            graphics.dispose();
        } else {
            // 添加图片水印:
            if (StringUtils.isEmpty(watermark)) {
                throw new RuntimeException("图片水印存放路径不能为空");
            }
            Image srcWatermark = readLocalPicture(watermark);
            int watermarkWidth = srcWatermark.getWidth(null);
            int watermarkHeight = srcWatermark.getHeight(null);
            // 设置 alpha 透明度:alpha 必须是范围 [0.0, 1.0] 之内(包含边界值)的一个浮点数字
            graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_ATOP, 0.9f));
            // 绘制水印图片  坐标为中间位置
            graphics.drawImage(srcWatermark, (imgWidth - watermarkWidth) / 2,
                    (imgHeight - watermarkHeight) / 2, watermarkWidth, watermarkHeight, null);
            graphics.dispose();
        }
        // 定义存储的地址
        String tarImgPath = "C:/Users/admin/Desktop/watermark.jpg";
        // 输出图片
        try {
            FileOutputStream outImgStream = new FileOutputStream(tarImgPath);
            ImageIO.write(bufImg, "png", outImgStream);
            outImgStream.flush();
            outImgStream.close();
            return "水印添加成功";
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

    /**
     * 添加水印
     *
     * @param pictureType   图片来源类型(1-本地图片 2-网络图片)
     * @param watermarkType 水印类型(1-文字水印 2-图片水印)
     * @param path          图片路径
     * @param watermark     水印内容(文字水印内容/图片水印的存放路径)
     */
    public static String addWatermark(Integer pictureType, Integer watermarkType, String path, String watermark) {
        if (null == pictureType) {
            throw new RuntimeException("图片来源类型不能为空");
        }
        if (null == watermarkType) {
            throw new RuntimeException("水印类型不能为空");
        }

        Image image;
        if (pictureType == 1) {
            // 读取本地图片
            image = readLocalPicture(path);
        } else {
            // 读取网络图片
            image = readNetworkPicture(path);
        }
        if (watermarkType == 1) {
            // 添加文字水印
            return manageWatermark(image, 1, watermark);
        } else {
            // 添加图片水印
            return manageWatermark(image, 2, watermark);
        }
    }

    /**
     * 获取水印文字的长度
     *
     * @param watermarkContent 文字水印内容
     * @param graphics         图像类
     */
    private static int getWatermarkLength(String watermarkContent, Graphics2D graphics) {
        return graphics.getFontMetrics(graphics.getFont()).charsWidth(watermarkContent.toCharArray(), 0, watermarkContent.length());
    }

    public static void main(String[] args) {

        // 本地图片路径:
        String localPath = "C:/Users/admin/Desktop/bg.jpg";
        // 网络图片地址:
        String networkPath = "https://img0.baidu.com/it/u=3708545959,316194769&fm=253&fmt=auto&app=138&f=PNG?w=1000&h=1000";
        // 文字水印内容
        String textWatermark = "Hello World!";
        // 图片水印路径
        String pictureWatermark = "C:\\Users\\admin\\Desktop\\wm.jpg";

        // 本地图片 添加文字水印
        //addWatermark(1, 1, localPath, textWatermark);

        // 网络图片 添加文字水印
        //addWatermark(2, 1, networkPath, textWatermark);

        // 本地图片 添加图片水印
        //addWatermark(1, 2, localPath, pictureWatermark);

        // 网络图片 添加图片水印
        addWatermark(2, 2, networkPath, pictureWatermark);

    }

}

如果这篇文章对您有所帮助,或者有所启发的话,求一键三连:点赞、评论、收藏➕关注,您的支持是我坚持写作最大的动力。 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1266949.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

python——第十四天

hash加密模块&#xff1a; hashlib hamc 加密那些事&#xff1a; 不可逆加密--hash加密 数据校验 密码加密 特点&#xff1a; 单向性 明文-->密文&#xff0c;但是密文无法还原成明文 唯一性 只要明文一致&#xff0c;得到的密文也是一定的 可逆加密&#xff1a; 对…

教师如何备课,上好一堂课

作为一名教师&#xff0c;备课是上好一堂课的关键。备课不仅仅是准备教材和教具&#xff0c;更是制定教学计划、设计教学方法、预测学生学习效果的重要环节。接下来我分享几点备课和上课的心得。 深入理解教学大纲 教学大纲是备课的指导性文件&#xff0c;只有深入理解教学大纲…

一文了解什么是Canvas

HTML5 Canvas是一个多功能元素&#xff0c;可以在网页上渲染图形、动画和图像。它提供了一个空白画布&#xff0c;开发人员可以在其中使用JavaScript绘制和操作像素、形状和文本。凭借其广泛的功能&#xff0c;HTML5 Canvas已成为创造视觉震撼和交互式网络体验的热门选择。 一、…

Matplotlib饼图的创建_Python数据分析与可视化

Matplotlib饼图的创建 饼图绘制饼图嵌套饼图 饼图 饼图又称圆饼图、圆形图等&#xff0c;它是利用圆形及圆内扇形面积来表示数值大小的图形。是将各项的大小与各项总和的比例显示在一张“饼”中&#xff0c;以“饼”的大小来确定每一项的占比。饼图主要用于总体中各组成部分所…

【linux】信号——信号产生

信号产生 1.预备知识2.信号产生2.1通过键盘发送信号2.2系统调用接口向进程发送信号2.3硬件异常产生信号2.4软件条件2.5总结 自我名言&#xff1a;只有努力&#xff0c;才能追逐梦想&#xff0c;只有努力&#xff0c;才不会欺骗自己。 喜欢的点赞&#xff0c;收藏&#xff0c;关…

区分(GIOU、DIOU、CIOU)(正则化、归一化、标准化)

一、IOU IoU 的全称为交并比&#xff08;Intersection over Union&#xff09;。IoU 计算的是 “预测的边框” 和 “真实的边框” 的交集和并集的比值。 1.GIOU&#xff1a;预测框&#xff08;蓝框&#xff09;和真实框&#xff08;绿框&#xff09;的最小外接矩形C。来获取预…

没想到吧!成功的图标设计,只需遵循这几个原则

图标在任何用户界面环境中都是不可或缺的元素。虽然许多图标小到可能被忽视&#xff0c;但它们在解决设计难题和用户体验问题上却起着决定性的作用。作为一名UI设计师&#xff0c;你必须要掌握的基本技巧之一就是图标设计。理解并应用图标设计的原则不仅可以帮助设计师快速定位…

如何有效地开发客户关系?

如何有效地开发客户关系&#xff1f; 有效地开发客户关系&#xff0c;是企业在竞争激烈的市场中获得优势的关键。通过深入了解客户需求、提供优质的产品和服务、建立良好的沟通渠道、提供个性化的体验以及建立长期合作关系等方式&#xff0c;企业可以有效地开发客户关系&#…

CSS特效020:涌动的弹簧效果

CSS常用示例100专栏目录 本专栏记录的是经常使用的CSS示例与技巧&#xff0c;主要包含CSS布局&#xff0c;CSS特效&#xff0c;CSS花边信息三部分内容。其中CSS布局主要是列出一些常用的CSS布局信息点&#xff0c;CSS特效主要是一些动画示例&#xff0c;CSS花边是描述了一些CSS…

WebUI自动化学习(Selenium+Python+Pytest框架)004

接下来&#xff0c;WebUI基础知识最后一篇。 1.下拉框操作 关于下拉框的处理有两种方式 &#xff08;1&#xff09;按普通元素定位 安装普通元素的定位方式来定位下拉框&#xff0c;使用元素的操作方法element.click()方法来操作下拉框内容的选择 &#xff08;2&#xff09…

Java容器合集

目录 浅谈 Array数组 初始化(动与静) 动态初始化 静态初始化 CRUD 增 查 索引取值 遍历 改 删 走进底层 栈与堆 一个数组的诞生 多数组 避坑指南 索引越界 空指针异常 小试牛刀 Collection List部落 介绍和特点 方法 ArrayList 介绍 方法 遍历 Li…

武汉凯迪正大KDZD5289硫化曲线测试仪(电脑无转子硫化仪)

电脑无转子硫化仪 硫化时间测试仪 硫化曲线仪 硫化曲线测试仪 武汉凯迪正大KDZD5289产品概述 KDZD5289硫化曲线测试仪&#xff08;电脑无转子硫化仪&#xff09;采用电脑控制进口温控仪进行准确控温&#xff0c;计算机适时进行数据处理并可进行统计、分析、存储对比等&#xff…

刚提离职,当天晚上公司就派人偷偷翻看我的电脑!

你被公司恶心过吗&#xff1f; 一位网友分享了被“恶心”的经历&#xff1a;提了离职&#xff0c;当天晚上电脑就被打开&#xff0c;提示有人登录自己微信&#xff0c;所有电脑记录都被偷偷翻看&#xff0c;她一怒之下在群里问&#xff0c;有人承认用了她的电脑&#xff0c;理由…

uniApp应用软件在运行时,未见向用户告知权限申请的目的,向用户索取(存储、相机、电话)等权限,不符合华为应用市场审核标准。

根据应用市场审核标准。我们开发的软件想要过审就必须要在应用在运行时&#xff0c;向用户告知权限申请的目的&#xff0c;向用户索取&#xff08;存储、相机、电话&#xff09;等权限&#xff01;&#xff01; 但是我们会发现做了提示弹框后又会驳回弹窗评频繁弹窗等等一系列…

【数据结构】单链表---C语言版

【数据结构】单链表---C语言版 一、顺序表的缺陷二、链表的概念和结构1.概念&#xff1a; 三、链表的分类四、链表的实现1.头文件&#xff1a;SList.h2.链表函数&#xff1a;SList.c3.测试函数&#xff1a;test.c 五、链表应用OJ题1.移除链表元素&#xff08;1&#xff09;题目…

Linux中的内存回收:Swap机制(图文并茂)

1、Swap机制是什么 &#xff1a; Swap机制是一种利用磁盘空间来扩展内存的方法。当系统的物理内存不足时&#xff0c;可以把一些不常用的内存数据写入到磁盘上的Swap分区&#xff0c;从而释放出更多的内存给其他需要的进程。当这些内存数据再次被访问时&#xff0c;系统会把它们…

多模态大模型总结2(主要2023年)

LLaVA-V1&#xff08;2023/04&#xff09; 论文&#xff1a;Visual Instruction Tuning 网络结构 如下图 所示为 LLaVA-v1 的模型结构&#xff0c;可以看出其简化了很多&#xff0c;但整体来说还是由三个组件构成&#xff1a; Vision Encoder&#xff1a;和 Flamingo 模型的 V…

Agent举例与应用

什么是Agent OpenAI 应用研究主管 Lilian Weng 在一篇长文中提出了 Agent LLM&#xff08;大型语言模型&#xff09;记忆规划技能工具使用这一概念&#xff0c;并详细解释了Agent的每个模块的功能。她对Agent未来的应用前景充满信心&#xff0c;但也表明到挑战无处不在。 现…

用VR+科普点亮科技之光VR航天科普体验巡展

11月22日至26日&#xff0c;第十一届中国(绵阳)科技城国际科技博览会圆满闭幕。本届科博会以“科技引领创新转化开放合作”为主题&#xff0c;创新办展办会模式&#xff0c;搭建高能级科技合作交流平台&#xff0c;展示了国内外科技创新发展成就和最新成果&#xff0c;举办了多…

铝合金轮毂金属部件全自动三维精密测量工业光学3d智能检测仪器-CASAIM-IS(2ND)

一、背景介绍 汽车轮毂是汽车零部件的重要组成部分。对于汽车而言&#xff0c;轮毂等同于腿对人的重要性。车辆将在行驶过程中产生横向和纵向载荷&#xff0c;车轮也将承受车辆和货物的所有载荷。随着汽车的速度越来越快&#xff0c;对车轮的动态稳定性和可靠性的要求也越来越…