You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

在Scala中使用circe解析含嵌套列表的递归JSON结构

基于circe的嵌套混合递归JSON结构解析方案

第一步:定义递归代数数据类型(ADT)

首先我们需要定义和JSON结构匹配的递归类型,覆盖args字段所有可能的取值形式:

sealed trait ArgEntry
// 对应单个节点对象
case class Node(name: String, args: List[ArgEntry]) extends ArgEntry
// 对应嵌套的列表结构
case class NestedArgs(items: List[ArgEntry]) extends ArgEntry

第二步:实现递归解码器

因为类型是递归引用的,所以需要用惰性求值的解码器避免初始化顺序问题,同时用or组合两种解码分支,优先匹配节点对象,匹配失败再尝试解析为嵌套列表:

import io.circe._
import io.circe.generic.semiauto._
import io.circe.parser._

object RecursiveJsonParser {
  implicit lazy val nodeDecoder: Decoder[Node] = deriveDecoder[Node]
  implicit lazy val argEntryDecoder: Decoder[ArgEntry] = 
    nodeDecoder.widen[ArgEntry] or 
    Decoder.decodeList(argEntryDecoder).map(NestedArgs).widen[ArgEntry]
}

第三步:测试解析效果

直接调用circe的解析API即可处理你给出的所有混合嵌套场景:

def main(args: Array[String]): Unit = {
  val targetJson = """{
    "name": "xx",
    "args": [
      {"name":"xy", "args": []},
      [
        {"name":"xy", "args": []},
        {"name":"xy", "args": [[]]}
      ],
      [
        [
          {"name":"xy", "args": [{"name":"xy", "args": []}]}
        ]
      ]
    ]
  }"""

  val parseResult = parse(targetJson).flatMap(_.as[Node])
  // 解析成功会返回Right包裹的Node实例,所有嵌套结构都会被正确映射
  println(parseResult)
}

可选:实现序列化编码器

如果需要将Scala结构转回JSON,可以按同样逻辑实现编码器:

implicit lazy val nodeEncoder: Encoder[Node] = deriveEncoder[Node]
implicit lazy val argEntryEncoder: Encoder[ArgEntry] = Encoder.instance {
  case n: Node => nodeEncoder(n)
  case NestedArgs(items) => Encoder.encodeList(argEntryEncoder).apply(items)
}

内容的提问来源于stack exchange,提问作者fr3ak

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.24 02:15:03