package com.ruoyi.reportrzs.service.impl;

import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.report.vo.ClassStatisticsInfoVo;
import com.ruoyi.reportrzs.domain.RzsClassStatisticsInfo;
import com.ruoyi.reportrzs.mapper.RzsClassStatisticsInfoMapper;
import com.ruoyi.reportrzs.service.IRzsClassStatisticsInfoService;
import com.ruoyi.system.domain.BladeRegion;
import com.ruoyi.system.service.IBladeRegionService;
import com.ruoyi.utils.BladeRegionUtils;

/**
 * 专利授权-分类统计Service业务层处理
 *
 * @author ruoyi
 * @date 2023-03-27
 */
@Service
public class RzsClassStatisticsInfoServiceImpl extends ServiceImpl<RzsClassStatisticsInfoMapper, RzsClassStatisticsInfo>
		implements IRzsClassStatisticsInfoService {

	private static final Logger logger = LoggerFactory.getLogger(RzsClassStatisticsInfoServiceImpl.class);

	@Autowired
	private IBladeRegionService bladeRegionService;
	@Autowired
	private RzsClassStatisticsInfoMapper rzsClassStatisticsInfoMapper;

	private void margeNotThisArea(List<Map> notThisAreaList, Map dataMap, Map<String, Map> alreadyNotThisArea, String areaCodeKey, String areaNameKey,
			String[] keys, String[] dataKeys) {
		StringBuffer keysb = new StringBuffer();
//		String areaCode = "000000";
		String areaCode = "非本区划";
		String areaName = "非本区划";
		keysb.append(areaCode).append("_").append(areaName);
		for (String key : keys) {
			String val = getStr(dataMap, key);
			if (StringUtils.isBlank(val)) {
				val = "null";
			}
			keysb.append("_").append(val);
		}
		if (!alreadyNotThisArea.containsKey(keysb.toString())) {
			Map newMap = new HashMap();
			newMap.putAll(dataMap);
			newMap.put(areaCodeKey, areaCode);
			newMap.put(areaNameKey, areaName);
			notThisAreaList.add(newMap);
			alreadyNotThisArea.put(keysb.toString(), newMap);
		} else {
			Map oldMap = alreadyNotThisArea.get(keysb.toString());
			for (String key : dataKeys) {
				long oldVal = getLong(oldMap, key);
				long newVal = getLong(dataMap, key);
				oldMap.put(key, oldVal + newVal);
			}
		}

	}

	private boolean isNotThisArea(Map map) {
		Object obj = map.get("not_this_area");
		if (obj != null) {
			return Boolean.parseBoolean(obj + "");
		}
		return false;
	}

	public Long sumByRank(RzsClassStatisticsInfo classStatisticsInfo) {
		return rzsClassStatisticsInfoMapper.sumByRank(classStatisticsInfo);
	}

	public List<ClassStatisticsInfoVo> listByReport(RzsClassStatisticsInfo classStatisticsInfo) {
		// TODO Auto-generated method stub
		String year = classStatisticsInfo.getYear();

		
		
		
		boolean retEmpty=false;
		if (StringUtils.isNotBlank(classStatisticsInfo.getCityCode()) && !"53".equals(classStatisticsInfo.getCityCode())) {
			String cityCode = classStatisticsInfo.getCityCode().trim();
			if(SecurityUtils.isNeedFilterByCityCode()) {
				String cc=SecurityUtils.needFilterByCityCode();
				if(!cc.equals(cityCode) ) {
					retEmpty=true;
				}
			}
		}else {
			if(SecurityUtils.isNeedFilterByCityCode()) {
				String cityCode=SecurityUtils.needFilterByCityCode();
				classStatisticsInfo.setCityCode(cityCode);
			}
		}
		
		
		String cityCode = null;

		if (StringUtils.isNotBlank(classStatisticsInfo.getCityCode()) && !"53".equals(classStatisticsInfo.getCityCode())) {
			cityCode = classStatisticsInfo.getCityCode().trim();
		}
		
		classStatisticsInfo.setCityCode(cityCode);
		List<Map> mapList = new ArrayList<Map>();
		if(!retEmpty) {
			mapList = rzsClassStatisticsInfoMapper.listByReport(classStatisticsInfo);
		}

		logger.debug("数据库数据加载完成，开始后续处理...");
		long begin = System.currentTimeMillis();
		// 处理非本区划
		boolean needSumNotThisArea = false;
		if (StringUtils.isNotBlank(cityCode)) {
			needSumNotThisArea = true;
		}
		List<Map> notThisAreaList = new ArrayList<Map>();
		Map<String, Map> alreadyNotThisArea = new HashMap<String, Map>();
		if (needSumNotThisArea && mapList != null && !mapList.isEmpty()) {
			List<Map> newList = new ArrayList<Map>();
			BladeRegionUtils.setNotThisArea(mapList, cityCode);
//			List<String> allCodes=bladeRegionService.getAllAreaCode();
//			Map<String,Boolean>alreadyMap=new HashMap<String,Boolean>();
			for (Map map : mapList) {
				String area_code = getStr(map, "area_code");
//				if (StringUtils.isBlank(area_code) || !area_code.startsWith(cityCode)) {
				if (isNotThisArea(map)) {
					// 合并到非本区化
					margeNotThisArea(notThisAreaList, map, alreadyNotThisArea, "area_code", "area_name", new String[] { "patent_type", "year" },
							new String[] { "total_cnt", "higher_school", "research_institute", "enterprise", "institutions", "individual" });
				} else {
					newList.add(map);// 不是非本区划
				}
			}
			mapList = newList;
			mapList.addAll(notThisAreaList);
		}

//		List<RzlClassStatisticsInfoVo> list = new ArrayList<RzlClassStatisticsInfoVo>();

		ClassStatisticsInfoVo total = new ClassStatisticsInfoVo();
		total.setYear(year);
		total.setTotalCnt(0L);
		total.setHigherSchool(0L);
		total.setResearchInstitute(0L);
		total.setEnterprise(0L);
		total.setInstitutions(0L);
		total.setIndividual(0L);
		total.setPatentType("总计");
		if (classStatisticsInfo.getCityCode() == null || "null".equals(classStatisticsInfo.getCityCode().trim())
				|| "".equals(classStatisticsInfo.getCityCode().trim())) {
			total.setAreaName("云南省");
		} else {
			BladeRegion bladeRegion = BladeRegionUtils.selectByCode(classStatisticsInfo.getCityCode());
			if (bladeRegion != null) {
				total.setAreaName(bladeRegion.getName());
			}
		}
//		list.add(total);

		// key:area 20231012 改为 area_code
		Map<String, List<ClassStatisticsInfoVo>> areaMap = new LinkedHashMap<String, List<ClassStatisticsInfoVo>>();

		// key:areaName_type
		Map<String, ClassStatisticsInfoVo> areaTypeMap = new HashMap<String, ClassStatisticsInfoVo>();
		// key:type
		Map<String, ClassStatisticsInfoVo> typeTotalMap = new LinkedHashMap<String, ClassStatisticsInfoVo>();

		for (Map itemMap : mapList) {

			String areaName = null;

			StringBuffer sb = new StringBuffer();
//			if (itemMap.containsKey("area_name")) {
//				areaName = itemMap.get("area_name").toString();
//			} else {
//				areaName = "null";
//			}

			if (itemMap.containsKey("area_code")) {
				areaName = itemMap.get("area_code").toString();
			} else {
				areaName = "null";
			}

			sb.append(areaName);
			sb.append("_");

			String patentType = null;
			if (itemMap.containsKey("patent_type")) {
				patentType = itemMap.get("patent_type").toString();
			} else {
				patentType = "null";
			}
			sb.append(patentType);

			String alreadyKey = sb.toString();

			ClassStatisticsInfoVo vo = null;
			if (areaTypeMap.containsKey(alreadyKey)) {
				vo = areaTypeMap.get(alreadyKey);
			} else {
				vo = new ClassStatisticsInfoVo();
				// list.add(vo);
				vo.setPatentType(patentType);
				areaTypeMap.put(alreadyKey, vo);

				if (!areaMap.containsKey(areaName)) {
					List<ClassStatisticsInfoVo> areaList = new ArrayList<ClassStatisticsInfoVo>();
					areaMap.put(areaName, areaList);
					areaList.add(vo);
				} else {
					areaMap.get(areaName).add(vo);
				}

			}

			vo.setYear(year);
			vo.setPatentType(getStr(itemMap, "patent_type"));
			vo.setTotalCnt(vo.getTotalCnt() + getLong(itemMap, "total_cnt"));
			vo.setHigherSchool(vo.getHigherSchool() + getLong(itemMap, "higher_school"));
			vo.setResearchInstitute(vo.getResearchInstitute() + getLong(itemMap, "research_institute"));
			vo.setEnterprise(vo.getEnterprise() + getLong(itemMap, "enterprise"));
			vo.setInstitutions(vo.getInstitutions() + getLong(itemMap, "institutions"));
			vo.setIndividual(vo.getIndividual() + getLong(itemMap, "individual"));
//			vo.setAreaName(getStr(itemMap, "area_name"));
			vo.setAreaName(getStr(itemMap, "area_code"));

//			total.setTotalCnt(total.getTotalCnt() + vo.getTotalCnt());
//			total.setHigherSchool(total.getHigherSchool() + vo.getHigherSchool());
//			total.setResearchInstitute(total.getResearchInstitute() + vo.getResearchInstitute());
//			total.setEnterprise(total.getEnterprise() + vo.getEnterprise());
//			total.setInstitutions(total.getInstitutions() + vo.getInstitutions());
//			total.setIndividual(total.getIndividual() + vo.getIndividual());
			
			total.setTotalCnt(total.getTotalCnt() + getLong(itemMap, "total_cnt"));
			total.setHigherSchool(total.getHigherSchool() + getLong(itemMap, "higher_school"));
			total.setResearchInstitute(total.getResearchInstitute() + getLong(itemMap, "research_institute"));
			total.setEnterprise(total.getEnterprise() + getLong(itemMap, "enterprise"));
			total.setInstitutions(total.getInstitutions() + getLong(itemMap, "institutions"));
			total.setIndividual(total.getIndividual() + getLong(itemMap, "individual"));
			
//			list.add(vo);
			// 总计
			ClassStatisticsInfoVo typeTotal = null;
			if (typeTotalMap.containsKey(patentType)) {
				typeTotal = typeTotalMap.get(patentType);
			} else {
				typeTotal = new ClassStatisticsInfoVo();

//				if(areaName==null || "null".equals(areaName.trim())  || "".equals(areaName.trim()) ) {
				typeTotal.setPatentType(patentType);
				total.setYear(year);
//				}

				typeTotalMap.put(patentType, typeTotal);
			}

//			typeTotal.setTotalCnt(typeTotal.getTotalCnt() + vo.getTotalCnt());
//			typeTotal.setHigherSchool(typeTotal.getHigherSchool() + vo.getHigherSchool());
//			typeTotal.setResearchInstitute(typeTotal.getResearchInstitute() + vo.getResearchInstitute());
//			typeTotal.setEnterprise(typeTotal.getEnterprise() + vo.getEnterprise());
//			typeTotal.setInstitutions(typeTotal.getInstitutions() + vo.getInstitutions());
//			typeTotal.setIndividual(typeTotal.getIndividual() + vo.getIndividual());
			
			typeTotal.setTotalCnt(typeTotal.getTotalCnt() + getLong(itemMap, "total_cnt"));
			typeTotal.setHigherSchool(typeTotal.getHigherSchool() + getLong(itemMap, "higher_school"));
			typeTotal.setResearchInstitute(typeTotal.getResearchInstitute() + getLong(itemMap, "research_institute"));
			typeTotal.setEnterprise(typeTotal.getEnterprise() + getLong(itemMap, "enterprise"));
			typeTotal.setInstitutions(typeTotal.getInstitutions() + getLong(itemMap, "institutions"));
			typeTotal.setIndividual(typeTotal.getIndividual() + getLong(itemMap, "individual"));
			
		}

//		Collections.sort(list,new VoComparator());

		// 处理小计
		for (Map.Entry<String, List<ClassStatisticsInfoVo>> ent : areaMap.entrySet()) {
//		for (String area : sortedKey(areaMap))  {
			List<ClassStatisticsInfoVo> areaList = ent.getValue();

			ClassStatisticsInfoVo tot = new ClassStatisticsInfoVo();

			String areaCode = ent.getKey();
			tot.setAreaName(areaCode);
			BladeRegion br2 = BladeRegionUtils.selectByCode(areaCode);
			if (br2 != null) {
				tot.setAreaName(br2.getDistrictShortName());
			}
			tot.setPatentType("总计");
			for (ClassStatisticsInfoVo vo : areaList) {
				tot.setTotalCnt(tot.getTotalCnt() + vo.getTotalCnt());
				tot.setHigherSchool(tot.getHigherSchool() + vo.getHigherSchool());
				tot.setResearchInstitute(tot.getResearchInstitute() + vo.getResearchInstitute());
				tot.setEnterprise(tot.getEnterprise() + vo.getEnterprise());
				tot.setInstitutions(tot.getInstitutions() + vo.getInstitutions());
				tot.setIndividual(tot.getIndividual() + vo.getIndividual());
			}
			areaList.add(0, tot);

		}

		// 结果列表
		List<ClassStatisticsInfoVo> list = new ArrayList<ClassStatisticsInfoVo>();
		
		if(!typeTotalMap.isEmpty()) {
			list.add(total);
		}
		
		list.addAll(typeTotalMap.values());
		Collections.sort(list, new ClassStatisticsInfoVo());

//		for (Map.Entry<String, List<ClassStatisticsInfoVo>> ent : areaMap.entrySet()) {
		List<String> keys=BladeRegionUtils.sortedKey(areaMap.keySet());
		for (String area : keys) {
			List<ClassStatisticsInfoVo> list1 = areaMap.get(area);
			List<ClassStatisticsInfoVo> shorted = getShortEd(list1);
			for (ClassStatisticsInfoVo vo : shorted) {
				if (!"总计".equals(vo.getPatentType())) {
					vo.setAreaName("");
				} else {
				}
				list.add(vo);
			}

		}
		long end = System.currentTimeMillis();
		logger.debug("处理完成，用时:" + (end - begin));
		return list;
	}

//	private static class SortedKeyData {
//		private String key;
//		private Integer sort;
//	}

//	private List<String> sortedKey(Map<String, List<ClassStatisticsInfoVo>> areaMap) {
//		logger.debug("开始执行sortedKey");
//		long begin = System.currentTimeMillis();
//		List<String> list = new ArrayList<String>();
//		if (areaMap == null) {
//			return list;
//		}
//		List<SortedKeyData> dataList = new ArrayList<SortedKeyData>();
//		for (String area : areaMap.keySet()) {
//			BladeRegion br = BladeRegionUtils.selectByCode(area);
//			SortedKeyData sd = new SortedKeyData();
//			sd.key = area;
//			if (br != null) {
//				sd.sort = br.getSort();
//			} else {
//				sd.sort = 0;
//			}
//			dataList.add(sd);
//		}
//
////		list.addAll(areaMap.keySet());
//		Collections.sort(dataList, new Comparator<SortedKeyData>() {
//			@Override
//			public int compare(SortedKeyData br1, SortedKeyData br2) {
//				// TODO Auto-generated method stub
////				BladeRegion br1=BladeRegionUtils.selectByCode(o1);
////				BladeRegion br2=BladeRegionUtils.selectByCode(o2);
//
//				if (br1 == null && br2 == null) {
//					return 0;
//				} else if (br1 == null) {
//					return -1;
//				} else if (br2 == null) {
//					return 1;
//				} else {
//					return br1.sort - br2.sort;
//				}
////				long total1 = ViewStatisticsInfoVo.getTotal(areaMap.get(o1));
////				long total2 = ViewStatisticsInfoVo.getTotal(areaMap.get(o2));
////				return (int)(total2 - total1);
//			}
//
//		});
//		for (SortedKeyData d : dataList) {
//			list.add(d.key);
//		}
//		logger.debug("sortedKey用时:" + (System.currentTimeMillis() - begin));
//		return list;
//
//	}

//	效率慢
//	private List<String> sortedKey(Map<String, List<ClassStatisticsInfoVo>> areaMap) {
//		logger.debug("开始执行sortedKey");
//		long begin=System.currentTimeMillis();
//		List<String> list = new ArrayList<String>();
//		if (areaMap == null) {
//			return list;
//		}
//		list.addAll(areaMap.keySet());
//		Collections.sort(list, new Comparator<String>() {
//			@Override
//			public int compare(String o1, String o2) {
//				// TODO Auto-generated method stub
//				logger.debug("do compare......");
//				BladeRegion br1=BladeRegionUtils.selectByCode(o1);
//				BladeRegion br2=BladeRegionUtils.selectByCode(o2);
//				
//				if(br1==null && br2==null) {
//					return 0;
//				}else if(br1==null) {
//					return -1;
//				}else if(br2==null) {
//					return 1;
//				}else {
//					return br1.getSort()-br2.getSort();
//				}
////				long total1 = ViewStatisticsInfoVo.getTotal(areaMap.get(o1));
////				long total2 = ViewStatisticsInfoVo.getTotal(areaMap.get(o2));
////				return (int)(total2 - total1);
//			}
//
//		});
//		logger.debug("sortedKey用时:"+(System.currentTimeMillis()-begin));
//		return list;
//
//	}

	private List<ClassStatisticsInfoVo> getShortEd(Collection<ClassStatisticsInfoVo> voList) {
		List<ClassStatisticsInfoVo> list = new ArrayList<ClassStatisticsInfoVo>();
		if (voList != null) {
			list.addAll(voList);
		}
		Collections.sort(list, new ClassStatisticsInfoVo());
		return list;
	}

	private String getStr(Map map, String key) {
		if (map == null || key == null || !map.containsKey(key)) {
			return "";
		}
		return map.get(key).toString();
	}

//	private int getInt(Map map, String key) {
//		if (map == null || key == null || !map.containsKey(key)) {
//			return 0;
//		}
//		return Integer.parseInt(map.get(key).toString());
//	}
	private long getLong(Map map, String key) {
		if (map == null || key == null || !map.containsKey(key)) {
			return 0L;
		}
		return Long.parseLong(map.get(key).toString());
	}

	/**
	 * 查询专利授权-分类统计列表
	 *
	 * @param rzsClassStatisticsInfo 专利授权-分类统计
	 * @return 专利授权-分类统计集合
	 * @date 2023-03-27
	 */
	@Override
	public List<RzsClassStatisticsInfo> queryList(RzsClassStatisticsInfo rzsClassStatisticsInfo) {
		QueryWrapper<RzsClassStatisticsInfo> queryWrapper = Wrappers.query();
		if (StringUtils.isNotNull(rzsClassStatisticsInfo.getCityCode())) {
			queryWrapper.eq("city_code", rzsClassStatisticsInfo.getCityCode());
		}
		if (StringUtils.isNotEmpty(rzsClassStatisticsInfo.getCityName())) {
			queryWrapper.like("city_name", rzsClassStatisticsInfo.getCityName());
		}
		if (StringUtils.isNotEmpty(rzsClassStatisticsInfo.getYear())) {
			queryWrapper.eq("year", rzsClassStatisticsInfo.getYear());
		}
		if (StringUtils.isNotEmpty(rzsClassStatisticsInfo.getMonth())) {
			queryWrapper.eq("month", rzsClassStatisticsInfo.getMonth());
		}
		if (StringUtils.isNotEmpty(rzsClassStatisticsInfo.getHigherSchool())) {
			queryWrapper.eq("higher_school", rzsClassStatisticsInfo.getHigherSchool());
		}
		if (StringUtils.isNotEmpty(rzsClassStatisticsInfo.getResearchInstitute())) {
			queryWrapper.eq("research_institute", rzsClassStatisticsInfo.getResearchInstitute());
		}
		if (StringUtils.isNotEmpty(rzsClassStatisticsInfo.getEnterprise())) {
			queryWrapper.eq("enterprise", rzsClassStatisticsInfo.getEnterprise());
		}
		if (StringUtils.isNotEmpty(rzsClassStatisticsInfo.getInstitutions())) {
			queryWrapper.eq("institutions", rzsClassStatisticsInfo.getInstitutions());
		}
		if (StringUtils.isNotEmpty(rzsClassStatisticsInfo.getIndividual())) {
			queryWrapper.eq("individual", rzsClassStatisticsInfo.getIndividual());
		}
		if (StringUtils.isNotEmpty(rzsClassStatisticsInfo.getTotal())) {
			queryWrapper.eq("total", rzsClassStatisticsInfo.getTotal());
		}
		if (StringUtils.isNotEmpty(rzsClassStatisticsInfo.getPatentType())) {
			queryWrapper.eq("patent_type", rzsClassStatisticsInfo.getPatentType());
		}
		if (StringUtils.isNotEmpty(rzsClassStatisticsInfo.getApplicantType())) {
			queryWrapper.eq("applicant_type", rzsClassStatisticsInfo.getApplicantType());
		}
		if (StringUtils.isNotNull(rzsClassStatisticsInfo.getStatus())) {
			queryWrapper.eq("status", rzsClassStatisticsInfo.getStatus());
		}
		queryWrapper.orderByDesc("id");
		return this.list(queryWrapper);
	}
}
