package com.huatek.busi.common.util;

import lombok.extern.slf4j.Slf4j;
import org.springframework.util.StringUtils;

import java.math.BigDecimal;
import java.util.Objects;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

/**
 * 工具类
 *
 * @author anker cheng
 *
 * @Date 2019年6月26日
 */
@Slf4j
public class DecimalUtil {

    private static Lock lock = new ReentrantLock();

    /**
     * 将字符串转成BigDecimal类型，如果val为空则返回defaultVal默认值
     * 
     * @param val        字符串
     * @param defaultVal 默认值
     * @return val对应的BigDecimal类型
     */
    public static BigDecimal getVal(String val, BigDecimal defaultVal) {
        return StringUtils.isEmpty(val) ? defaultVal : new BigDecimal(val);
    }

    public static BigDecimal getVal(BigDecimal val, BigDecimal defaultVal) {
        return val == null ? defaultVal : val;
    }

    public static BigDecimal getVal(Integer val, BigDecimal defaultVal) {
        return val == null ? defaultVal : BigDecimal.valueOf(val);
    }
    
    public static BigDecimal getVal(Long val, BigDecimal defaultVal) {
        return val == null ? defaultVal : BigDecimal.valueOf(val);
    }

    /**
     * 将字符串转成BigDecimal类型，如果val为空则返回 BigDecimal.ZERO
     * 
     * @param val 字符串
     * @return val对应的BigDecimal类型
     */
    public static BigDecimal getVal(String val) {
        return getVal(val, BigDecimal.ZERO);
    }

    public static BigDecimal getVal(BigDecimal val) {
        return getVal(val, BigDecimal.ZERO);
    }

    public static BigDecimal getVal(Integer val) {
        return getVal(val, BigDecimal.ZERO);
    }

    public static BigDecimal getVal(Long val) {
        return getVal(val, BigDecimal.ZERO);
    }

    /**
     * 除运算
     * 
     * @param dividend
     *            被除数
     * @param divisor
     *            除数
     * @param scale
     *            小数位数(精度)
     * @return 除运算结果
     */
    public static BigDecimal divide(BigDecimal dividend, BigDecimal divisor, int scale) {
        if (divisor == null || BigDecimal.ZERO.compareTo(divisor) == 0) {
            throw new IllegalArgumentException("除数不能为0");
        }
        return dividend.divide(divisor, scale, BigDecimal.ROUND_HALF_UP);
    }

    public static String toStr(BigDecimal val) {
        return val == null ? null : val.toString();
    }
    
    public static String calIncrease(BigDecimal nowVal, String preValStr) {
        BigDecimal preVal = getVal(preValStr);
        if (BigDecimal.ZERO.compareTo(preVal) == 0) {
            return "0";
        }
        BigDecimal result = divide(nowVal.subtract(preVal), preVal, 4);
        return toStr(result);
    }

    /**
     * 自增数字
     * @param num
     * @return
     */
    public static String autoNumber(Long num){
        String code = null;
        if(lock.tryLock()){
            try {
                log.info("<<<<<<<<<<<<<<获取锁>>>>>>>>>>>>>>>>>>>");
                if(Objects.isNull(num) || num == 0){
                    code = "0001";
                }else {
                    int len = String.valueOf(num).length();
                    if(len > 0){
                        switch (len){
                            case 1:
                                if(num == 9){
                                    code = "00" + (num + 1);
                                }else {
                                    code = "000" + (num + 1);
                                }
                                break;
                            case 2:
                                if(num == 99){
                                    code = "0" + (num + 1);
                                }else {
                                    code = "00" + (num + 1);
                                }
                                break;
                            case 3:
                                if(num == 999){
                                    code = String.valueOf(num + 1);
                                }else {
                                    code = "0" + (num + 1);
                                }
                                break;
                            default:
                                code = String.valueOf(num + 1);
                        }
                    }
                }
            }catch (Exception e){
                log.error("执行自增方法异常:{}", e);
            }finally {
                log.info("<<<<<<<<<<<<<<释放锁>>>>>>>>>>>>>>>>>>>");
                lock.unlock();
            }
        }else {
            log.info("<<<<<<<<<<<<<<未获取锁>>>>>>>>>>>>>>>>>>>");
        }
        return code;
    }
}