package com.njcn.advance.event.cause.core;

import com.njcn.advance.event.cause.model.DataFeature;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * 阈值判决器
 * 对应C语言中的threshold_judge函数
 */
public class ThresholdJudge {
    private static final Logger logger = LoggerFactory.getLogger(ThresholdJudge.class);

    /**
     * 阈值判断确定暂降原因
     * @param result 特征分析结果
     * @return 判断状态码
     */
    public static int thresholdJudge(DataFeature result) {
        int checkStatus = 0;
        
        // 初始化为未知原因
        result.setCause(DataFeature.CAUSE_TYPE0);
        
        // 暂降前不平衡度超限判断，可能存在异常
        if (result.getPreBphErr() == 1) {
            checkStatus = 1;
            logger.info("检测到暂降前不平衡异常");
            return checkStatus;
        }
        
        // 持续时间判断
        if (result.getHoldTime() < (result.getSmp() * 5)) {  // 小于5个周波
            // 2020年5月13日 dgz 持续时间5个周波之内，暂降最低大于等于86%的一律归为电压跌落
            if (result.getU3Min() >= 0.86f) {
                result.setCause(DataFeature.CAUSE_TYPE4);
                checkStatus = 2;
                logger.info("判断为电压跌落: u3Min={}", result.getU3Min());
                return checkStatus;
            } else if ((result.getBi1() > 0.5f) && (result.getU3Min() < 0.7f)) {
                result.setCause(DataFeature.CAUSE_TYPE1);
                checkStatus = 10;
                logger.info("判断为短路故障: bi1={}, u3Min={}", result.getBi1(), result.getU3Min());
                return checkStatus;
            } else {
                // 暂降很浅判断为电压跌落
                result.setCause(DataFeature.CAUSE_TYPE4);
                checkStatus = 2;
                logger.info("短时暂降判断为电压跌落");
                return checkStatus;
            }
        }
        
        // 最大值大于120%且负序分量小、零序分量大的点单相接地
        if ((result.getU3Max() > 1.2f) && (result.getU2Avg() < 0.05f) && (result.getU0Avg() > 0.05f)) {
            result.setCause(DataFeature.CAUSE_TYPE1);
            checkStatus = 3;
            logger.info("判断为单相接地短路: u3Max={}, u2Avg={}, u0Avg={}", 
                       result.getU3Max(), result.getU2Avg(), result.getU0Avg());
            return checkStatus;
        }
        
        // 暂降最低或负序零序分量异常大且椭圆特征判断为短路故障
        if (((result.getU3Min() < 0.7f) || (result.getU2Avg() > 0.1f) || (result.getU0Avg() > 0.1f)) && 
            (result.getBi1() > 0.5f)) {
            result.setCause(DataFeature.CAUSE_TYPE1);
            checkStatus = 4;
            logger.info("判断为短路故障: u3Min={}, u2Avg={}, u0Avg={}, bi1={}", 
                       result.getU3Min(), result.getU2Avg(), result.getU0Avg(), result.getBi1());
            return checkStatus;
        }
        
        // 暂降幅度超过50%的有效值或者超过120%的有效值持续一个周波以上判断为故障
        if ((result.getuLow50() == 1) || (result.getuHigh120() == 1)) {
            result.setCause(DataFeature.CAUSE_TYPE1);
            checkStatus = 9;
            logger.info("判断为短路故障: 电压超限 uLow50={}, uHigh120={}", 
                       result.getuLow50(), result.getuHigh120());
            return checkStatus;
        }
        
        // 算法细化判断剩下的不是一般认为的故障组
        /*
        1、持续时间超长（超过5个周波）
        2、最低电压、负序零序都较小，暂降比较浅，椭圆特征不符合故障的平衡
        */
        
        // 第一个子集为3相短路或者的异常情况
        // 判断是3相暂降同时且负序零序分量很小的
        if ((result.getUMin()[0] < 0.9f) && (result.getUMin()[1] < 0.9f) && (result.getUMin()[2] < 0.9f) &&
            (result.getU2Avg() < 0.02f) && (result.getU0Avg() < 0.02f)) {
            
            // 判断恢复特征奇异值和持续时间为感动电机
            if ((result.getHoldTime() > (result.getSmp() * 50 * 5)) && (result.getSvd() < 0.015f)) {
                result.setCause(DataFeature.CAUSE_TYPE3);
                checkStatus = 5;
                logger.info("判断为感应电机启动: holdTime={}, svd={}", result.getHoldTime(), result.getSvd());
                return checkStatus;
            } else {
                result.setCause(DataFeature.CAUSE_TYPE1);
                checkStatus = 6;
                logger.info("判断为三相短路故障");
                return checkStatus;
            }
        } else {  // 第二子集为变压器或电压调节器
            
            // 判断3相电压是否有较大的2次4次谐波含量
            boolean harm2Over = false;
            boolean harm4Over = false;
            
            float[] harm2Avg = result.getHarm2Avg();
            float[] harm4Avg = result.getHarm4Avg();
            
            if ((harm2Avg[0] > 0.04f) && (harm2Avg[1] > 0.04f) && (harm2Avg[2] > 0.04f)) {
                harm2Over = true;
            }
            if ((harm4Avg[0] > 0.04f) && (harm4Avg[1] > 0.04f) && (harm4Avg[2] > 0.04f)) {
                harm4Over = true;
            }
            
            // 判断2次和4次谐波含量超标(且暂降前偶次谐波)，持续时间超过5个周波，椭圆特征判断为电压调节器
            if ((harm2Over || harm4Over) && (result.getPreHarmErr() == 0) && 
                (result.getHoldTime() > (result.getSmp() * 5)) && (result.getBi1() < 0.4f) && 
                (result.getU3Max() < 1.1f) && (result.getU3Min() > 0.7f)) {
                
                result.setCause(DataFeature.CAUSE_TYPE2);
                checkStatus = 7;
                logger.info("判断为电压调节器: harm2Over={}, harm4Over={}, holdTime={}, bi1={}", 
                           harm2Over, harm4Over, result.getHoldTime(), result.getBi1());
                return checkStatus;
            } else {
                result.setCause(DataFeature.CAUSE_TYPE1);
                checkStatus = 8;
                logger.info("其他情况判断为短路故障");
                return checkStatus;
            }
        }
    }

    /**
     * 获取原因描述
     * @param cause 原因代码
     * @return 原因描述
     */
    public static String getCauseDescription(int cause) {
        switch (cause) {
            case DataFeature.CAUSE_TYPE0:
                return "未知原因";
            case DataFeature.CAUSE_TYPE1:
                return "短路故障";
            case DataFeature.CAUSE_TYPE2:
                return "电压调节器";
            case DataFeature.CAUSE_TYPE3:
                return "感应电机启动";
            case DataFeature.CAUSE_TYPE4:
                return "电压跌落";
            default:
                return "未定义原因";
        }
    }
}