BaseUtils.java 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541
  1. package org.springblade.common.utils;
  2. import com.alibaba.cloud.commons.lang.StringUtils;
  3. import org.checkerframework.checker.regex.RegexUtil;
  4. import org.springblade.common.constant.RegexConstant;
  5. import org.springblade.common.vo.DataVO;
  6. import java.io.*;
  7. import java.math.BigDecimal;
  8. import java.math.BigInteger;
  9. import java.math.RoundingMode;
  10. import java.security.MessageDigest;
  11. import java.time.LocalDate;
  12. import java.time.format.DateTimeFormatter;
  13. import java.util.*;
  14. import java.util.regex.Matcher;
  15. import java.util.regex.Pattern;
  16. import java.util.stream.Collectors;
  17. import java.util.stream.IntStream;
  18. import static java.math.BigDecimal.*;
  19. /**
  20. * @author yangyj
  21. * @Date 2022/7/8 11:08
  22. * @description 基础工具类
  23. */
  24. public class BaseUtils {
  25. public static DateTimeFormatter chineseDateFm = DateTimeFormatter.ofPattern("yyyy年M月d日", Locale.CHINA);
  26. public static Pattern KM = Pattern.compile(RegexConstant.KM_REG);
  27. public static double k2d(Object k) {
  28. Matcher mt = KM.matcher(k.toString());
  29. if (mt.find()) {
  30. return Double.parseDouble(mt.group(1)) * 1000 + Double.parseDouble(mt.group(2));
  31. }
  32. return -1;
  33. }
  34. public static Double milestone(String s){
  35. Pattern pattern=Pattern.compile("(?i)K(\\d+)\\+([\\d.]+)");
  36. Matcher matcher = pattern.matcher(s);
  37. if(matcher.find()){
  38. return Double.parseDouble(matcher.group(1))*1000+ Double.parseDouble(matcher.group(2));
  39. }
  40. return null;
  41. }
  42. /**
  43. * @return java.util.Map<java.lang.String, java.lang.String>
  44. * @Description 将key1(val1)key2(val2)key3(val3)...这种格式的参数转换为Map
  45. * @Param [str]
  46. * @Author yangyj
  47. * @Date 2022.08.12 10:39
  48. **/
  49. public static Map<String, String> string2Map(String str) {
  50. Map<String, String> result = new HashMap<>(15);
  51. if (StringUtils.isNotEmpty(str)) {
  52. String[] args = str.split("\\)");
  53. for (String a : args) {
  54. if (StringUtils.isNotEmpty(a)) {
  55. String[] kv = a.split("\\(");
  56. result.put(kv[0], kv[1]);
  57. }
  58. }
  59. }
  60. return result;
  61. }
  62. /**
  63. * @return java.lang.Boolean
  64. * @Description 基础数据类型批量非空判断
  65. * @Param [args]
  66. * @Author yangyj
  67. * @Date 2022.08.26 11:14
  68. **/
  69. public static Boolean isNotNull(Object... args) {
  70. if (args != null) {
  71. for (Object obj : args) {
  72. if (obj == null || "".equals(obj)) {
  73. return false;
  74. }
  75. }
  76. return true;
  77. }
  78. return false;
  79. }
  80. /*将不同长度的字符串转换为固定长度的Long*/
  81. public static long str2Long(String input) {
  82. try {
  83. MessageDigest md = MessageDigest.getInstance("SHA-256");
  84. byte[] hash = md.digest(input.getBytes());
  85. BigInteger bigInt = new BigInteger(1, hash);
  86. // 取正整数
  87. return bigInt.longValue() & Long.MAX_VALUE;
  88. } catch (Exception e) {
  89. throw new RuntimeException(e);
  90. }
  91. }
  92. /*最小分割片*/
  93. public static int sliceNumber(Integer len,Integer capacity){
  94. return (int)Math.ceil(len/(double)capacity);
  95. }
  96. /**
  97. * @Description 判断对象是否为数值
  98. * @Param [value]
  99. * @Author yangyj
  100. * @Date 2023.01.17 13:48
  101. **/
  102. static final String NUM_REG = "^[+-]?\\d+(\\.\\d+)?$";
  103. public static boolean isNumber(Object value) {
  104. if ((value == null) ) {
  105. return false;
  106. }
  107. String stringValue = value.toString().trim();
  108. if (stringValue.isEmpty()) {
  109. return false;
  110. }
  111. if (value instanceof Number) {
  112. return true;
  113. }
  114. return Pattern.matches(NUM_REG,stringValue);
  115. }
  116. public static boolean isNotNumber(Object value){
  117. return !isNumber(value);
  118. }
  119. public static BigDecimal str2BigDecimal(Object s){
  120. if(s instanceof BigDecimal){
  121. return (BigDecimal) s;
  122. }
  123. if(isNumber(s)){
  124. return new BigDecimal(s.toString());
  125. }else{
  126. return ZERO;
  127. }
  128. }
  129. /*默认返回零*/
  130. public static Double obj2DoubleZero(Object obj) {
  131. if(obj instanceof Double){
  132. return (Double) obj;
  133. }
  134. if(isNumber(obj)){
  135. if(obj instanceof Number){
  136. if(obj instanceof BigDecimal){
  137. return str2BigDecimal(obj).doubleValue();
  138. }
  139. return (double) obj;
  140. }
  141. return Double.parseDouble(obj.toString());
  142. }
  143. return 0D;
  144. }
  145. /*默认返回零*/
  146. public static Integer obj2IntegerZero(Object obj) {
  147. if(isNumber(obj)){
  148. if(obj instanceof Number){
  149. if(obj instanceof BigDecimal){
  150. return str2BigDecimal(obj).intValue();
  151. }
  152. return (int) obj;
  153. }
  154. return Integer.parseInt(obj.toString());
  155. }
  156. return 0;
  157. }
  158. /**
  159. * @Description 根据指定大小对LIST进行切分
  160. * @Param [list, chunkSize:每一段长度]
  161. * @return java.util.List<java.util.List<T>>
  162. * @Author yangyj
  163. * @Date 2023.07.03 13:46
  164. **/
  165. public static <T> List<List<T>> splitList(List<T> list, int chunkSize) {
  166. return IntStream.range(0, (list.size() + chunkSize - 1) / chunkSize)
  167. .mapToObj(i -> list.subList(i * chunkSize, Math.min((i + 1) * chunkSize, list.size())))
  168. .collect(Collectors.toList());
  169. }
  170. /**
  171. * @Description 深度拷贝
  172. * @Param [originalList]
  173. * @return java.util.List<T>
  174. * @Author yangyj
  175. * @Date 2023.04.28 14:18
  176. **/
  177. public static <T extends Serializable> List<T> copyList(List<T> originalList) {
  178. try {
  179. ByteArrayOutputStream baos = new ByteArrayOutputStream();
  180. ObjectOutputStream oos = new ObjectOutputStream(baos);
  181. oos.writeObject(originalList);
  182. oos.close();
  183. ByteArrayInputStream bais = new ByteArrayInputStream(baos.toByteArray());
  184. ObjectInputStream ois = new ObjectInputStream(bais);
  185. @SuppressWarnings("unchecked")
  186. List<T> copiedList = (List<T>) ois.readObject();
  187. ois.close();
  188. return copiedList;
  189. } catch (Exception e) {
  190. e.printStackTrace();
  191. }
  192. return null;
  193. }
  194. public static String handleNull(Object obj) {
  195. if (null == obj) {
  196. return "";
  197. } else {
  198. return obj.toString().trim();
  199. }
  200. }
  201. public static boolean isNotEmpty(Object value) {
  202. if(value!=null){
  203. if(value instanceof List&&((List<?>) value).size()>0 ){
  204. return true;
  205. }else if(value instanceof Map&&((Map<?, ?>) value).size()>0){
  206. return true;
  207. }else {
  208. return value.toString().trim().length() > 0;
  209. }
  210. }
  211. return false;
  212. }
  213. public static boolean isEmpty(Object value){
  214. return !isNotEmpty(value);
  215. }
  216. public static List<Integer> coords2Int(String coords){
  217. Matcher mx = matcher("([A-Z]{1,3})(\\d{1,3})[~|\\-|,|#]([A-Z]{1,3})(\\d{1,3})",coords);
  218. List<Integer> list = new ArrayList<>();
  219. if(mx.find()) {
  220. list.add(Integer.parseInt(mx.group(1)));
  221. list.add(Integer.parseInt(mx.group(2)));
  222. list.add(Integer.parseInt(mx.group(3)));
  223. list.add(Integer.parseInt(mx.group(4)));
  224. }
  225. return list;
  226. }
  227. public static Matcher matcher(String regex, String value) {
  228. Pattern pattern = Pattern.compile(regex);
  229. return pattern.matcher(value);
  230. }
  231. public static Double[] scopeParse(Object dev, Object design, Object xN) {
  232. if (isNotEmpty(dev)) {
  233. Double[] result = new Double[2];
  234. double designD = Double.parseDouble(design.toString());
  235. double xND = Double.parseDouble(xN.toString());
  236. String devStr = dev.toString();
  237. devStr = devStr.replaceAll("[\\[\\]]+", "");
  238. double min = 0;
  239. double max = 0;
  240. devStr = devStr.replaceAll("\\s+", "");
  241. if (devStr.contains("≤") || devStr.contains("<=") || devStr.contains("<")||devStr.contains("≦")) {
  242. devStr = devStr.replace("≤", "").replace("<=", "").replace("≦","");
  243. max = designD + Double.parseDouble(devStr) * xND;
  244. } else if (devStr.contains("≥") || devStr.contains(">=") || devStr.contains(">")) {
  245. devStr = devStr.replace("≥", "").replace(">=", "");
  246. min = designD + Double.parseDouble(devStr) * xND;
  247. max = Double.MAX_VALUE;
  248. } else if (devStr.contains(",") || devStr.contains(",")) {
  249. String[] arr = devStr.split("[,,]");
  250. min = designD + Double.parseDouble(arr[0]) * xND;
  251. max = designD + Double.parseDouble(arr[1]) * xND;
  252. } else if (devStr.contains("%")) {
  253. devStr = devStr.replace("%", "");
  254. double devD = Math.abs(Double.parseDouble(devStr) * designD / 100);
  255. min = designD - devD;
  256. max = designD + devD;
  257. } else if (devStr.contains("±")) {
  258. devStr = devStr.replace("±", "");
  259. double devD = Math.abs(Double.parseDouble(devStr) * xND);
  260. min = designD - devD;
  261. max = designD + devD;
  262. }
  263. if(min>max){
  264. double tmp=max;
  265. max=min;
  266. min=tmp;
  267. }
  268. result[0] = min;
  269. result[1] = max;
  270. return result;
  271. }
  272. return null;
  273. }
  274. public static Integer handleObj2Integer(Object obj) {
  275. if (null == obj) {
  276. return 0;
  277. } else {
  278. double value;
  279. try {
  280. value = Double.parseDouble(obj.toString());
  281. } catch (Exception ex) {
  282. value = 0;
  283. }
  284. return (int) value;
  285. }
  286. }
  287. /**
  288. * @return java.util.List<java.lang.Object> 不能包含0
  289. * @Description specifiedRangeList
  290. * @Param [hz:频率, design:设计值, dev:偏差范围, xN 偏差范围单位和设计值单位的比值,例如毫米:厘米=0.1, scale:保存小数位, passRate:合格率[0,1]]
  291. * @Author yangyj
  292. * @Date 2022.03.31 09:16
  293. **/
  294. public static List<Object> rangeList(Object hz, Object design, Object dev, Object xN, Object scale, Object passRate) {
  295. List<Object> result = new ArrayList<>();
  296. if (isNotNull(design, dev, hz)) {
  297. if (isEmpty(scale)) {
  298. scale = 0;
  299. }
  300. if (isEmpty(passRate)) {
  301. passRate = 1;
  302. }
  303. if (isEmpty(xN)) {
  304. xN = 1;
  305. }
  306. Double[] range = scopeParse(dev, design, xN);
  307. int scaleI = Integer.parseInt(scale.toString());
  308. int min = 0, max = 0;
  309. assert range != null;
  310. if (range.length > 0) {
  311. min = (int) (range[0] * Math.pow(10, scaleI));
  312. max = (int) (range[1] * Math.pow(10, scaleI));
  313. }
  314. Random rd = new Random();
  315. int hzi = new BigDecimal(hz.toString()).multiply(new BigDecimal(passRate.toString())).setScale(0, ROUND_CEILING).intValue();
  316. int loop=200;
  317. for (int i = 0; i < hzi; i++) {
  318. BigDecimal tb = new BigDecimal(rd.nextInt(max - min + 1) + min).divide(BigDecimal.valueOf(Math.pow(10, scaleI)), scaleI, ROUND_HALF_UP);
  319. if(tb.compareTo(BigDecimal.ZERO)==0&&loop>0){
  320. loop--;
  321. i--;
  322. }else{
  323. if (scaleI > 0) {
  324. result.add(tb.doubleValue());
  325. } else {
  326. result.add(tb.intValue());
  327. }
  328. }
  329. }
  330. int total = handleObj2Integer(hz);
  331. if (total - hzi > 0) {
  332. loop=200;
  333. for (int k = 0; k < total - hzi; k++) {
  334. BigDecimal tb;
  335. if (rd.nextBoolean()) {
  336. tb = new BigDecimal(rd.nextInt(((max - min) / 2)) + max + 1).divide(BigDecimal.valueOf(Math.pow(10, scaleI)), scaleI, ROUND_HALF_UP);
  337. } else {
  338. tb = new BigDecimal(min - 1 - rd.nextInt(((max - min) / 2))).divide(BigDecimal.valueOf(Math.pow(10, scaleI)), scaleI, ROUND_HALF_UP);
  339. }
  340. if(tb.compareTo(BigDecimal.ZERO)==0&&loop>0){
  341. loop--;
  342. k--;
  343. }else {
  344. if (scaleI > 0) {
  345. result.add(tb.doubleValue());
  346. } else {
  347. result.add(tb.intValue());
  348. }
  349. }
  350. }
  351. if (result.size()>0) {
  352. Collections.shuffle(result);
  353. }
  354. }
  355. }
  356. return result;
  357. }
  358. /*是否包含链*/
  359. public static boolean notInChain(List<String> cp,String s){
  360. if(cp!=null&& isNotEmpty(s)){
  361. if(cp.size()==0){
  362. /*空结合*/
  363. return true;
  364. }else{
  365. /*没有一个已知路径包含*/
  366. return cp.stream().noneMatch(c->c.contains(s));
  367. }
  368. }
  369. return false;
  370. }
  371. public static boolean inChain(List<String> cp,String s){
  372. if(cp!=null&& isNotEmpty(s)){
  373. if(cp.size()==0){
  374. /*空结合*/
  375. return true;
  376. }else{
  377. /*没有一个已知路径包含*/
  378. return cp.stream().anyMatch(s::contains);
  379. }
  380. }
  381. return false;
  382. }
  383. public static boolean inChain(String[] cp,String s){
  384. if(cp!=null&&cp.length>0&& s!=null&&s.length()>0){
  385. return inChain(Arrays.asList(cp), s);
  386. }
  387. return false;
  388. }
  389. public static Integer getScale(Object... number) {
  390. int max = 0;
  391. if (number != null) {
  392. return getScale(scaleParam(number),1);
  393. }
  394. return max;
  395. }
  396. /**保留有效数字后面的0*/
  397. public static Integer getScaleZero(Object... number){
  398. int max = 0;
  399. if (number != null) {
  400. return getScale(scaleParam(number),0);
  401. }
  402. return max;
  403. }
  404. public static boolean containsZH(Object chars) {
  405. Matcher m = Pattern.compile("[\u4e00-\u9fa5]").matcher(handleNull(chars));
  406. return m.find();
  407. }
  408. /* public static void main(String[] args) {
  409. System.out.println(getScaleZero(152000,"±10.0"));
  410. System.out.println(getScaleZero(152000,"-10.0,10"));
  411. System.out.println(getScaleZero(152000,"-10.0,10.0"));
  412. System.out.println(getScaleZero(Double.MAX_VALUE,"-10.0,10"));
  413. System.out.println(getScaleZero(152000,"-10,10"));
  414. }*/
  415. public static List<Object> obj2List(Object obj) {
  416. List<Object> result = new ArrayList<>();
  417. if (obj != null) {
  418. List<Object> datas = new ArrayList<>();
  419. if (obj instanceof List) {
  420. datas = (List<Object>) obj;
  421. } else {
  422. datas.add(obj);
  423. }
  424. if (isNotEmpty(datas)) {
  425. for (Object e : datas) {
  426. boolean fi = isNotEmpty(e) && !containsZH(e.toString()) && (e.toString().contains("、") || e.toString().contains(",") || e.toString().contains(" ") || e.toString().contains(","));
  427. if (fi) {
  428. String s = e.toString().trim();
  429. if (s.contains(" ")) {
  430. s = s.replaceAll("\\s+", "、");
  431. }
  432. Object[] bs = s.split("[、,,]");
  433. result.addAll(Arrays.asList(bs));
  434. } else {
  435. result.add(e);
  436. }
  437. }
  438. }
  439. }
  440. return result;
  441. }
  442. public static List<Object> obj2ListNe(Object obj) {
  443. List<Object> list = obj2List(obj);
  444. return list.parallelStream().filter(BaseUtils::isNotEmpty).collect(Collectors.toList());
  445. }
  446. public static List<Object> scaleParam(Object ... number){
  447. return Arrays.stream(number).filter(BaseUtils::isNotEmpty).flatMap(e-> BaseUtils.obj2ListNe(e).stream()).distinct().map(s->s.toString().replaceAll("±","")).filter(BaseUtils::isNumber).map(e->{
  448. /*0.3999999999999986 检测到超长小数位先转double处理,再还原回String*/
  449. String tg=e.toString();
  450. int dot=tg.indexOf(".");
  451. boolean unlimited=dot>0&&(tg.length()-dot>6);
  452. if(unlimited||tg.contains("e")){
  453. return BigDecimal.valueOf(Double.parseDouble(tg)).setScale(2, RoundingMode.HALF_UP).toString();
  454. }else {
  455. return e;
  456. }
  457. }).collect(Collectors.toList());
  458. }
  459. public static final String[] SCALE_REG=new String[]{"(\\d)+.(\\d)*[0-9]","(\\d)+.(\\d)*[1-9]"};
  460. private static Integer getScale(List<Object> number,Integer zero){
  461. int max=0;
  462. if(isNotEmpty(number)){
  463. for (Object n : number) {
  464. if (isNotEmpty(n)) {
  465. String[] sa = n.toString().split(",");
  466. for (String s : sa) {
  467. Matcher m = Pattern.compile(SCALE_REG[zero]).matcher(s);
  468. if (m.find()) {
  469. int cp = new StringBuilder(m.group()).reverse().toString().indexOf(".");
  470. if (cp < 5) {
  471. max = Math.max(cp, max);
  472. }
  473. }
  474. }
  475. }
  476. }
  477. }
  478. return max;
  479. }
  480. private static final String COLUMN_REG = "^[A-Z]{0,2}$";
  481. /*列名转int*/
  482. public static int parseColumn(String column) {
  483. int value = -1;
  484. if (StringUtils.isNotEmpty(column)) {
  485. column = column.trim();
  486. if (column.matches(COLUMN_REG)) {
  487. char[] columnCh = column.toCharArray();
  488. for (char ch : columnCh) {
  489. //字母, 最长只考虑双字母的
  490. if (ch >= 65 && ch <= 90) {
  491. if (value > 0) {
  492. value = (26 * value) + (ch - 64);
  493. } else {
  494. value = ch - 64;
  495. }
  496. }
  497. }
  498. }
  499. }
  500. return value - 1;
  501. }
  502. public static String toDateStr(LocalDate date){
  503. return Optional.ofNullable(date).orElse(LocalDate.now()).format(chineseDateFm);
  504. }
  505. }