Java中如何将类JSON无引号字符串转为键值对提取attempt字段
类JSON字符串提取字段最优方案
核心思路
你所持有的串外层是无引号键值对、用等号赋值的类JSON结构,内部嵌套的value字段已经是合法JSON格式,可根据需要提取的字段数量选择以下两种方案:
方案1:全量转标准JSON后解析(推荐多字段提取场景)
先通过简单的正则替换把整个串转为合法JSON,再用JSON序列化库反序列化为对象/Map结构,后续可灵活提取任意字段,容错性和扩展性更高。
Java示例代码(基于Gson)
import com.google.gson.Gson; import com.google.gson.JsonArray; import com.google.gson.JsonObject; import java.util.Map; public class ParseInvalidJson { public static void main(String[] args) { // 原始类JSON字符串 String rawStr = "[{type=Callback, output=[{name=prompt, value=InputCode}], input=[{name=IDT1, value=}]}, {type=TextOutputCallback, output=[{name=message, value={\"current_type\":\"Code\",\"info\":{\"some_key\":\"cf2fc86a\",\"some_type\":\"Code\",\"ph_no\":\"111111111\"},\"attempt\":2}}]}]"; // 三步转换为合法JSON // 1. 替换所有等号为冒号 String step1 = rawStr.replace('=', ':'); // 2. 给所有未加双引号的键名包裹双引号 String step2 = step1.replaceAll("([a-zA-Z0-9_]+)(?=\\s*:)", "\"$1\""); // 3. 补全空值的双引号 String standardJson = step2.replaceAll(":(\\s*[,}])", ":\"\"$1"); // 解析为JSON数组 Gson gson = new Gson(); JsonArray rootArray = gson.fromJson(standardJson, JsonArray.class); // 定位到内部的message对应的value对象 JsonObject textOutputCallback = rootArray.get(1).getAsJsonObject(); JsonObject messageValue = textOutputCallback.getAsJsonArray("output") .get(0).getAsJsonObject() .get("value").getAsJsonObject(); // 提取attempt字段,也可直接转为Map调用get方法 Map<String, Object> msgMap = gson.fromJson(messageValue, Map.class); String attempt = msgMap.get("attempt").toString(); System.out.println(attempt); // 输出结果:2 } }
方案2:正则直接提取(推荐单字段快速提取场景)
如果只需要提取attempt这一个字段,不需要处理其他结构,可直接用正则匹配目标字段,代码更轻量,执行效率更高。
Java示例代码
import java.util.regex.Matcher; import java.util.regex.Pattern; public class ExtractSingleField { public static void main(String[] args) { String rawStr = "[{type=Callback, output=[{name=prompt, value=InputCode}], input=[{name=IDT1, value=}]}, {type=TextOutputCallback, output=[{name=message, value={\"current_type\":\"Code\",\"info\":{\"some_key\":\"cf2fc86a\",\"some_type\":\"Code\",\"ph_no\":\"111111111\"},\"attempt\":2}}]}]"; // 匹配attempt字段的数值 Pattern pattern = Pattern.compile("\"attempt\"\\s*:\\s*(\\d+)"); Matcher matcher = pattern.matcher(rawStr); if (matcher.find()) { String attempt = matcher.group(1); System.out.println(attempt); // 输出结果:2 } } }
内容的提问来源于stack exchange,提问作者Billy
相关产品推荐
相关产品推荐

