根據模板提取變量信息
阿新 • • 發佈:2018-11-07
app 完美 pla 精神 提交 由於 基礎 mage ace
問題來源:
最近公司要做短信中轉服務平臺,由於是第一次接觸這個業務,中間跳了不少坑,其中有一部分就是:上遊通道需要配置信息模板,接口中提供可變信息即可;下遊通道則是只能提供完整信息,無法提供可變信息(吐槽一下:就是太LAN,不想弄而已),沒有辦法,只好由我們自己完成可變信息的提取,然後將可變信息以固定格式提交到上遊通道,可變信息後面統稱為變量信息。
經過努力,完成了一個測試類,可以根據完整信息內容和模板來自動提取出內容中的變量信息,並可以根據完整信息的長度來自動將模板分割成兩條或更多,以及對應條數的變量信息,話不多說,直接上代碼:
package com.hyfd.service; import java.util.ArrayList; import java.util.List; public class ArgsGet { // 滿足信息分割條件的長度(這裏設置為滿100字符即進行分割) private static final int STR_SPLIT_MAX_LENGTH = 100; public static void main(String[] args) { String smsStr = ToDBC("成吉思汗的騎兵,***速度與二十世紀的裝甲部隊相當;北宋的床弩,射程達" + "一千五百米,與二十世紀的狙擊×××差不多;但這些仍不過是古代的騎兵與×××而已,不可能與" + "現代力量抗衡。基礎理論決定一切,未來史學派清楚地看到了這一點。而你們,卻被回光返照的" + "低級技術蒙住了眼睛。你們躺在現代文明的溫床中安於享樂,對即將到來的決定人類命運的終極" + "決戰完全沒有精神上的準備。"); getArgsList(smsStr); } /** * <h5>功能:獲取信息拆分後的變量信息</h5> * @param smsStr 完整信息內容 */ private static List<String> getArgsList(String smsStr) { String ptTemplateAll = "#*#的騎兵,***速度與#*#世紀的裝甲部隊相當;#*#的#*#,射程達#*#米," + "與#*#世紀的#*#差不多;但這些仍不過是古代的#*#與#*#而已,不可能與#*#力量抗衡。#*#決" + "定一切,#*#清楚地看到了這一點。而你們,卻被回光返照的#*#蒙住了眼睛。你們躺在#*#的溫床" + "中安於#*#,對即將到來的決定人類命運的#*#完全沒有精神上的準備。"; String[] ptTemplate = ptTemplateAll.split("#\\*#"); System.out.println("完整信息[" + smsStr + "]"); System.err.println("完整模板[" + ptTemplateAll + "]"); // 拆分信息內容 List<String> smsList = smsSplit(smsStr, ptTemplate); // 根據信息內容拆分模板 List<List<String>> templateSplit = templateSplist(smsList, ptTemplate); for (int i = 0; i < templateSplit.size(); i++) { System.out.println("第" + (i + 1) + "段拆分模板" + templateSplit.get(i) + ""); } List<String> argsList = new ArrayList<String>(); // 根據拆分後的信息內容和模板獲取對應的變量信息 for (int i = 0; i < smsList.size(); i++) { String tempSmsStr = smsList.get(i); List<String> templateSplist = templateSplit.get(i); for (String template : templateSplist) { if (!"".equals(template)) { tempSmsStr = tempSmsStr.replaceFirst(template, ","); } } if (tempSmsStr.endsWith(",")) { tempSmsStr = tempSmsStr.substring(0, tempSmsStr.length() - 1); } argsList.add(tempSmsStr); System.err.println("第" + (i + 1) + "段變量信息[" + tempSmsStr + "]"); } return argsList; } /** * <h5>功能:拆分信息內容</h5> * @param smsStr 完整信息內容 * @param ptTemplate 數組化的模板信息 * @return */ private static List<String> smsSplit(String smsStr, String[] ptTemplate){ List<String> smsList = new ArrayList<String>(); StringBuffer sbf = new StringBuffer(); for (String template: ptTemplate) { if (!"".equals(template)) { // 一旦信息內容長度超過100,則進行信息拆分 if (sbf.length() > STR_SPLIT_MAX_LENGTH) { // System.out.println(sbf.toString()); smsList.add(sbf.toString()); sbf.setLength(0); } sbf.append(smsStr.substring(0, smsStr.indexOf(template) + template.length())); smsStr = smsStr.substring(smsStr.indexOf(template)+template.length()); } } smsList.add(sbf.toString()); return smsList; } /** * <h5>功能:根據信息內容拆分模板</h5> * @param smsList 拆分後的信息內容 * @param ptTemplate 模板信息 * @return */ private static List<List<String>> templateSplist(List<String> smsList, String[] ptTemplate){ List<List<String>> templateList = new ArrayList<List<String>>(); for (String smsStr : smsList) { // System.out.println(smsStr); // 1.獲取信息結束標識 String sbf = ""; for (String template : ptTemplate) { if (!"".equals(template)) { if (smsStr.endsWith(template)) { // System.out.println(template+"="+smsStr.indexOf(template)); sbf = template; } } } // 2.根據信息標識,將信息模板進行對應的拆分 List<String> tempList = new ArrayList<String>(); StringBuffer tempSbf = new StringBuffer(); for (int i = 0; i < ptTemplate.length; i++) { tempSbf.append(ptTemplate[i]); if (!"".equals(tempSbf.toString())) { tempList.add(tempSbf.toString()); if (sbf.equals(tempSbf.toString())) { ptTemplate[i] = ""; break; } else { ptTemplate[i] = ""; } } tempSbf.setLength(0); } templateList.add(tempList); // System.out.println(JSONObject.toJSONString(tempList)); // System.out.println("-----------------------------"); } return templateList; } /** * <h5>功能:全角轉半角</h5> * 這個主要是為了規範信息內容,因此對全角信息做了半角處理,不用的時候從引用的地方直接去掉即可 * @author zhangpj @date 2018年11月5日 * @param str * @return */ public static String ToDBC(String str) { char[] c = str.toCharArray(); for (int i = 0; i < c.length; i++) { // 全角空格為12288,半角空格為32 if (c[i] == 12288) { c[i] = (char) 32; continue; } // 其他字符半角(33-126)與全角(65281-65374)的對應關系是:均相差65248 if (c[i] > 65280 && c[i] < 65375) c[i] = (char) (c[i] - 65248); } return new String(c); } }
測試結果,可以看到模板分段並完美的獲取到了對應的變量信息,效果如下
後記
由於趕時間沒有做優化,如果有不當之處,歡迎各位大神指教,謝謝!
根據模板提取變量信息