package com.zksy.gas.utils;

/**
 * @Description
 * @Date 2025- 03-06-上午 9:02
 * @auther tuDouSi
 */
public class DataCheckUtil {
    /**
     *
     * @description: crc16校验,输入一个数据,返回一个数组.
     * @param str
     * @return 返回两个校验码,低字节在前,高字节在后
     *
     */
    public static String crc16(String str) {
        int[] data = hexStringToIntArray(str);
        int xda, xdapoly;
        int i, j, xdabit;
        xda = 0xFFFF;
        xdapoly = 0xA001;
        for (i = 0; i < data.length; i++) {
            xda ^= data[i];
            for (j = 0; j < 8; j++) {
                xdabit = (int) (xda & 0x01);
                xda >>= 1;
                if (xdabit == 1) {
                    xda ^= xdapoly;
                }
            }
        }
        byte[] temdata = new byte[2];
        temdata[0] = (byte) (xda & 0xFF);
        temdata[1] = (byte) (xda >> 8);
        return bytesToHexString(temdata);
    }
    /**
     *
     * @description: crc16校验,
     * @param str
     * @return 返回两个校验码,高字节在前,低字节在后
     *
     */
    public static String crc16Tall(String str) {
        int[] data = hexStringToIntArray(str);
        int xda, xdapoly;
        int i, j, xdabit;
        xda = 0xFFFF;
        xdapoly = 0xA001;
        for (i = 0; i < data.length; i++) {
            xda ^= data[i];
            for (j = 0; j < 8; j++) {
                xdabit = (int) (xda & 0x01);
                xda >>= 1;
                if (xdabit == 1) {
                    xda ^= xdapoly;
                }
            }
        }

        // 关键修改：先放高位字节，再放低位字节
        byte[] temdata = new byte[2];
        temdata[0] = (byte) (xda >> 8);  // 高位字节
        temdata[1] = (byte) (xda & 0xFF); // 低位字节

        return bytesToHexString(temdata);
    }
    // 将十六进制字符串转换为整数数组
    private static int[] hexStringToIntArray(String str) {
        if (str.length() % 2 != 0) {
            throw new IllegalArgumentException("Hex string length must be even");
        }

        int[] result = new int[str.length() / 2];
        for (int i = 0; i < str.length(); i += 2) {
            result[i / 2] = Integer.parseInt(str.substring(i, i + 2), 16);
        }
        return result;
    }

    // 将字节数组转换为十六进制字符串
    private static String bytesToHexString(byte[] bytes) {
        StringBuilder sb = new StringBuilder();
        for (byte b : bytes) {
            sb.append(String.format("%02X", b));
        }
        return sb.toString();
    }

    public static int calcChecksum(byte[] data, int offset, int length) {
        int sum = 0;
        for (int i = offset; i < offset + length; i++) {
            sum += (data[i] & 0xFF);
        }
        return (0xFF - (sum & 0xFF)) & 0xFF;
    }
    /**
     * 仅对数据累加后取低8位
     * @param data 待计算字节数组
     * @param offset 起始索引
     * @param length 计算长度
     * @return 8位校验结果
     */
    static int calcSumOnly(byte[] data, int offset, int length) {
        int sum = 0;
        for (int i = offset; i < offset + length; i++) {
            sum += (data[i] & 0xFF); // 累加每个字节的无符号值
        }
        return sum & 0xFF; // 仅取低8位，无FF-操作
    }
}
