Java常用工具类集合

1.线程池工具类

package com.idc.utils;

import lombok.extern.slf4j.Slf4j;

import java.util.concurrent.LinkedBlockingDeque;
import java.util.concurrent.ThreadFactory;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicInteger;

/**
 * @author yming wang
 * @date 2023/8/15 10:14
 * @desc
 */
@Slf4j
public class CommonsThreadPoolUtils {

    /**
     * CPU核数
     */
    private static final int CPU_NUMS = Runtime.getRuntime().availableProcessors();

    /**
     * 最大线程数
     */
    private static final int MAXIMUM_POOL_SIZE = CPU_NUMS * 2 + 1;

    /**
     * 等待队列长度
     */
    private static final int BLOCKING_QUEUE_LENGTH  = 1000;

    /**
     * 闲置线程存活时间
     */
    private static final int KEEP_ALIVE_TIME = 60;

    /**
     * 闲置线程存活时间单位
     */
    private static final TimeUnit  KEEP_ALIVE_TIME_UNIT = TimeUnit.SECONDS;

    /**
     * 线程名称
     */
    private static final String THREAD_NAME = "CommonsThreadPoolUtils";

    /**
     * 线程执行器
     */
    private static ThreadPoolExecutor executor;

    /**
     * @params:
     * @return null
     * @author yming wang
     * @date 2023/8/15 10:42
     * @desc 构造器私有化,阻止外部直接实例化对象
     */
    private CommonsThreadPoolUtils(){
        
    }

    /**
     * @params:
     * @return java.util.concurrent.ThreadPoolExecutor
     * @author yming wang
     * @date 2023/8/15 11:00
     * @desc 获取单例线程池对象-单例双重校验
     */
    public static ThreadPoolExecutor getThreadPool() {
        if (executor == null) {
            synchronized (CommonsThreadPoolUtils.class) {
                if (executor == null) {
                    executor = new ThreadPoolExecutor(
                            //核心线程数
                            MAXIMUM_POOL_SIZE - 1,
                            //最大线程数
                            MAXIMUM_POOL_SIZE,
                            //活跃时间
                            KEEP_ALIVE_TIME,
                            //活跃时间单位
                            KEEP_ALIVE_TIME_UNIT,
                            //线程队列
                            new LinkedBlockingDeque<>(BLOCKING_QUEUE_LENGTH),
                            //线程工厂
                            new DefaultThreadFactory(THREAD_NAME),
                            //队列已满,而且当前线程数已超过最大线程数时的异常处理策略(自定义拒绝策略)
                            new ThreadPoolExecutor.AbortPolicy() {
                                @Override
                                public void rejectedExecution(Runnable r, ThreadPoolExecutor e) {
                                    log.warn("线程等待队列已满,当前运行线程总数:{},活动线程数:{},等待运行任务数:{}",  e.getPoolSize(),  e.getActiveCount(), e.getQueue().size());
                                }
                            });
                }
            }
        }
        return executor;
    }

    /**
     * @params: 
     * @param runnable
     * @return
     * @author yming wang
     * @date 2023/8/15 11:16
     * @desc 向线程池提交一个任务,不关心处理结果
     */
    public static void execute(Runnable runnable) {
        if (runnable != null) {
            getThreadPool().execute(runnable);
        }
    }

    /**
     * @params:
     * @param runnable
     * @return
     * @author yming wang
     * @date 2023/8/15 11:15
     * @desc 从线程队列中移除任务
     */
    public static void cancel(Runnable runnable) {
        if (executor != null) {
            getThreadPool().getQueue().remove(runnable);
        }
    }

    /**
     * @params:
     * @return int
     * @author yming wang
     * @date 2023/8/15 11:15
     * @desc 获取当前线程池线程数量
     */
    public static int getSize() {
        return getThreadPool().getPoolSize();
    }

    /**
     * @params:
     * @return
     * @author yming wang
     * @date 2023/8/15 12:30
     * @desc 关闭线程池
     */
    public static void shutdown() {
        if (!getThreadPool().isShutdown()) {
            getThreadPool().shutdown();
        }
    }

    /**
     * @params:
     * @return int
     * @author yming wang
     * @date 2023/8/15 11:15
     * @desc 获取当前活动的线程数量
     */
    public static int getActiveCount() {
        return getThreadPool().getActiveCount();
    }

    /**
     * @author yming wang
     * @desc 默认线程池工厂
     */
    static class DefaultThreadFactory implements ThreadFactory {
        private static final AtomicInteger poolNumber = new AtomicInteger(1);
        private final ThreadGroup group;
        private final AtomicInteger threadNumber = new AtomicInteger(1);
        private final String namePrefix;

        DefaultThreadFactory(String name) {
            SecurityManager s = System.getSecurityManager();
            group = (s != null) ? s.getThreadGroup() : Thread.currentThread().getThreadGroup();
            namePrefix = name + "-pool-" + poolNumber.getAndIncrement() + "-thread-";
        }

        @Override
        public Thread newThread(Runnable r) {
            Thread t = new Thread(group, r,namePrefix + threadNumber.getAndIncrement(),0);
            if (t.isDaemon()){
                t.setDaemon(false);
            }
            if (t.getPriority() != Thread.NORM_PRIORITY){
                t.setPriority(Thread.NORM_PRIORITY);
            }
            return t;
        }
    }
}


2.POI Excel工具类

package com.jwyy.utils;

import com.jwyy.model.ExcelModel;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.io.IOUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.poifs.filesystem.POIFSFileSystem;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.springframework.web.multipart.MultipartFile;

import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.text.DecimalFormat;
import java.util.ArrayList;
import java.util.List;

/**
 * @author yming wang
 * @date 2023/9/11 9:10
 * @desc
 */
@Slf4j
public class ExcelUtils {

    private static final String excel07 = "xlsx";
    private static final String excel03 = "xls";
    private static final int skipRow = 2;

    public static List<ExcelModel> readExcel(String filePath) {
        String fileSuffix = filePath.substring(filePath.lastIndexOf('.') + 1);
        if (!excel07.equalsIgnoreCase(fileSuffix) && !excel03.equalsIgnoreCase(fileSuffix)) {
           throw new RuntimeException("不支持的格式,请上传xls或xlsx格式的文件");
        }

        List<ExcelModel> values = null;
        try (FileInputStream fileInputStream = new FileInputStream(filePath)) {
            values = readExcel(fileSuffix, fileInputStream);
        } catch (Exception e) {
            log.error("读取excel出现异常:", e);
        }
        return values;
    }

    public static List<ExcelModel> readExcel(MultipartFile file) throws IOException {
        String filePath = file.getOriginalFilename();
        String fileSuffix = filePath.substring(filePath.lastIndexOf('.') + 1);
        return readExcel(fileSuffix,file.getInputStream());
    }

    public static List<ExcelModel> readExcel(String fileSuffix, InputStream inputStream) {
        Workbook workbook = null;
        POIFSFileSystem fileSystem = null;
        List<ExcelModel> values = null;

        try {
            if (excel07.equalsIgnoreCase(fileSuffix)) {
                workbook = new XSSFWorkbook(inputStream);
            } else if (excel03.equalsIgnoreCase(fileSuffix)) {
                fileSystem = new POIFSFileSystem(inputStream);
                workbook = new HSSFWorkbook(fileSystem);
            }

            if (null == workbook) {
                throw new RuntimeException("excel读取类型错误");
            }

            values = getValue(workbook,skipRow);

        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            IOUtils.closeQuietly(workbook);
            IOUtils.closeQuietly(fileSystem);
        }
        return values;
    }

    private static List<ExcelModel> getValue(Workbook workbook,int skipRow) {
        Sheet sheet = workbook.getSheetAt(workbook.getActiveSheetIndex());
        int lastRow = sheet.getLastRowNum();
        List<ExcelModel> values = new ArrayList<>();
        for (int i = skipRow; i <= lastRow; i++) {
            Row row = sheet.getRow(i);
            if (null == row) {
                continue;
            }
            //excel与model映射
            ExcelModel excelModel = buildExcelModel(row);
            values.add(excelModel);
        }
        //封装跨行数据
        fillExcelModel(values);
        return values;
    }

    private static ExcelModel buildExcelModel(Row row){
        short cellNum = row.getLastCellNum();
        ExcelModel rowValue = new ExcelModel();
        for (int j = 0; j <= cellNum; j++) {
            Cell cell = row.getCell(j);
            if (null != cell) {
                Field[] fields = rowValue.getClass().getDeclaredFields();
                for (Field field : fields) {
                    ExcelModel.ExcelProperty excelProperty = field.getDeclaredAnnotation(ExcelModel.ExcelProperty.class);
                    if (excelProperty != null && excelProperty.index() == j) {
                        try {
                            String name = field.getName();
                            String setterMethod = "set" + name.substring(0, 1).toUpperCase() + name.substring(1);
                            Method method = rowValue.getClass().getDeclaredMethod(setterMethod, String.class);
                            method.invoke(rowValue, getCellValue(cell));
                        } catch (Exception e) {
                            log.error("反射封装属性错误:", e);
                        }
                    }
                }
            }
        }
        return rowValue;
    }

    private static void fillExcelModel(List<ExcelModel> values){
        //指标名称
        String orderNumber = null;
        //指标名称
        String targetName = null;
        //目标值
        String targetValue = null;
        //指标配分
        String targetGrate = null;
        //指标定义
        String targetDefinition = null;
        //评分方式
        String scoringMethod = null;
        //填充
        for (int i = 0; i < values.size(); i++) {
            ExcelModel excelModel = values.get(i);
            if (StringUtils.isNotBlank(excelModel.getOrderNumber())){
                orderNumber = excelModel.getOrderNumber();
            }else{
                excelModel.setOrderNumber(orderNumber);
            }
            if (StringUtils.isNotBlank(excelModel.getTargetName())){
                targetName = excelModel.getTargetName();
            }else{
                excelModel.setTargetName(targetName);
            }
            if (StringUtils.isNotBlank(excelModel.getTargetValue())){
                targetValue = excelModel.getTargetValue();
            }else{
                excelModel.setTargetValue(targetValue);
            }
            if (StringUtils.isNotBlank(excelModel.getTargetGrate())){
                targetGrate = excelModel.getTargetGrate();
            }else{
                excelModel.setTargetGrate(targetGrate);
            }
            if (StringUtils.isNotBlank(excelModel.getTargetDefinition())){
                targetDefinition = excelModel.getTargetDefinition();
            }else{
                excelModel.setTargetDefinition(targetDefinition);
            }
            if (StringUtils.isNotBlank(excelModel.getScoringMethod())){
                targetDefinition = excelModel.getScoringMethod();
            }else{
                excelModel.setScoringMethod(scoringMethod);
            }
        }
    }

    private static String getCellValue(Cell cell) {
        if (cell == null) {
            return "";
        }
        Object value = "";
        switch (cell.getCellType()) {
            case BLANK:
                break;
            case ERROR:
                value = cell.getErrorCellValue();
                break;
            case STRING:
                value = cell.getStringCellValue();
                break;
            case BOOLEAN:
                value = cell.getBooleanCellValue();
                break;
            case NUMERIC:
                value = cell.getNumericCellValue();
                DecimalFormat df = new DecimalFormat("0");
                value = df.format(value);
                break;
            case _NONE:
        }

        return String.valueOf(value);
    }
}

@Data
public class ExcelModel {

    @Target(ElementType.FIELD)
    @Retention(RetentionPolicy.RUNTIME)
    public @interface ExcelProperty{
        int index();
        String value();
    }

    @TableId(type = IdType.AUTO)
    private String id;

    /**
     * 序号
     */
    @ExcelProperty(index = 0,value = "序号")
    private String orderNumber;
}

3.自定义token工具类

@Slf4j
public class TwoFactorTokenUtils {

    /**
     * userId - userToken
     */
    private static Map<String, String> userToken = new HashMap<>(8);

    /**
     * userToken - userToken的失效时间
     */
    private static Map<String, Long> tokenInvalid = new HashMap<>(8);

    /**
     * 失效时间
     */
    private static long expireTime = 1000 * 60 * 30;

    /**
     * userToken续签时间
     */
    private static long refreshTime = 1000 * 60 * 5;

    public static boolean checkToken(String token) {
        //刷新token
        refresh(token);
        //输出最新token信息
        printTokenInfo();
        return tokenInvalid.containsKey(token);
    }

    public static void add(String userId, String token) {
        userToken.put(userId, token);
        //30分钟后自动过期
        tokenInvalid.put(token, System.currentTimeMillis() + expireTime);
        log.info("用户userId:{},生成token:{}", userId, token);
    }

    public static void remove(String userId) {
        String token = userToken.remove(userId);
        tokenInvalid.remove(token);
        log.info("删除用户userId:{},token:{}", userId, token);
    }

    public static void refresh(String token) {
        synchronized (TwoFactorTokenUtils.class){
            Long currTokenExpireTime = tokenInvalid.get(token);
            int secondUnit = 1000;
            //token续签
            if (currTokenExpireTime != null && ((currTokenExpireTime - System.currentTimeMillis()) / secondUnit) <= (refreshTime / secondUnit)) {
                log.info("token:{}续签成功", token);
                tokenInvalid.put(token, System.currentTimeMillis() + expireTime);
            }
            //同步token信息
            Set<String> userIds = new HashSet<>();
            Iterator<Map.Entry<String, String>> userTokenItr = userToken.entrySet().iterator();
            while (userTokenItr.hasNext()) {
                Map.Entry<String, String> nextToken = userTokenItr.next();
                //用户id
                String userId = nextToken.getKey();
                //用户token
                String userToken = nextToken.getValue();
                //用户token失效时间
                Long tokenExpireTime = tokenInvalid.get(userToken);
                //检验token是否过期
                if (tokenExpireTime != null && ((tokenExpireTime - System.currentTimeMillis()) / secondUnit) <= 0) {
                    userIds.add(userId);
                }
            }
            for (String userId : userIds) {
                log.info("用户userId:{},token已过期", userId);
                remove(userId);
            }
        }
    }

    public static String generateToken(){
       return UUID.randomUUID().toString().replaceAll("-", "");
    }

    public static void printTokenInfo(){
        Iterator<Map.Entry<String, String>> iterator = userToken.entrySet().iterator();
        log.info("====================在线用户列表====================");
        while (iterator.hasNext()){
            Map.Entry<String, String> next = iterator.next();
            log.info("当前在线userId:{},token:{}",next.getKey(),next.getValue() );
        }
    }

    /**
     * demo
     */
    public static void main(String[] args) throws InterruptedException {

        TwoFactorTokenUtils.add("10001", "10001-token-id");
        TwoFactorTokenUtils.add("10002", "10002-token-id");
        TwoFactorTokenUtils.add("10003", "10003-token-id");

        int i = 0;
        while (true) {
            Thread.sleep(1000);
            log.info("模拟web server 运行......" + i);
            TwoFactorTokenUtils.checkToken("10001-token-id");
            if (i == 121) {
                TwoFactorTokenUtils.checkToken("10002-token-id");
                TwoFactorTokenUtils.checkToken("10003-token-id");
            }
            i++;
        }
    }
}

4.动态数组工具类

@Slf4j
public class DataMonitorUtils {

    private int position;

    private int minCount;

    private int capacity;

    private int[] array;

    public DataMonitorUtils(int capacity, int minCount) {
        this.capacity = capacity;
        this.minCount = minCount;
        this.position = 0;
        this.array = new int[capacity];
    }

    /**
     * @param data
     * @return
     * @params:
     * @author yming wang
     * @date 2023/7/20 13:32
     * @desc 添加监控数据
     */
    public void push(int data, Consumer<String> messageConsumer) {
        if (this.position >= this.array.length) {
            //容量超出,实现位移
            for (int i = 0; i < this.position; i++) {
                if (i < this.position - 1) {
                    this.array[i] = this.array[i + 1];
                } else {
                    this.array[this.position - 1] = data;
                }
            }
        } else {
            //保存数据
            this.array[this.position++] = data;
        }
        //触发短信
        if (this.position == this.array.length && this.check()) {
            this.sendMsg(messageConsumer);
            this.reset();
        }
    }

    /**
     * @return
     * @params:
     * @author yming wang
     * @date 2023/7/20 13:32
     * @desc 重置
     */
    public void reset() {
        this.position = 0;
        for (int i = 0; i < this.array.length; i++) {
            this.array[i] = 0;
        }
    }

    /**
     * @return boolean
     * @params:
     * @author yming wang
     * @date 2023/7/20 13:30
     * @desc 容器从数据都小于最小值发送告警
     */
    public boolean check() {
        for (int i = 0; i < this.array.length; i++) {
            if (this.array[i] > minCount) {
                return false;
            }
        }
        return true;
    }

    /**
     * @return
     * @params:
     * @author yming wang
     * @date 2023/7/20 13:30
     * @desc 打印数据
     */
    public void print() {
        log.info("====================遍历数据集合=========================");
        for (int i = 0; i < this.array.length; i++) {
            log.info("打印数据array[{}] = {}", i, this.array[i]);
        }
    }

    /**
     * @param messageConsumer
     * @return
     * @params:
     * @author yming wang
     * @date 2023/7/20 13:34
     * @desc 发送短信
     */
    public void sendMsg(Consumer<String> messageConsumer) {
        String message = "this is a message";
        messageConsumer.accept(message);
        log.info("this is a message log");
    }
}
  • 11
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值