Отключение узла общего дерева в Scala - PullRequest
0 голосов
/ 11 октября 2018

Рассмотрим следующий стандартный класс:

class Node(val data: NodeData, val children: Seq[Node])

Класс NodeData также прост:

case class NodeData(text: String, foo: List[Bar])

Кроме того, дерево имеет произвольную глубину, оно не зафиксировано.

Понятно, что поиск в этой структуре с первым дыханием или с глубиной вначале тривиален с идиоматической Scala.Тем не менее, учтите, что я хочу не только посещать каждый из этих узлов, но и изменять их при каждом посещении.Более конкретно, я хочу изменить объект в этом списке foo.Как бы я пошел на реализацию этого?Один из способов, которым я подумал об этом, - каким-то образом обновить узлы и построить новое дерево, обходя его, но моя интуиция подсказывает мне, что есть более простое решение, чем это.

1 Ответ

0 голосов
/ 11 октября 2018

Если вы действительно хотите остаться неизменным, я бы определил функцию recMap на Node, например:

def recMap(f: NodeData => NodeData) : Node = Node(f(data), children.map(_.recMap(f)))

Затем вы можете использовать ее, как в этом примере (я сделал Node кейс тоже):

type Bar = Int

case class NodeData(text: String, foo: List[Bar])

case class Node(data: NodeData, children: Seq[Node]) {

  def recMap(f: NodeData => NodeData) : Node = Node(f(data), children.map(_.recMap(f)))
}

val tree = new Node(NodeData("parent", List(1, 2, 3, 4)), Seq(
  Node(NodeData("a child", List(5, 6, 7, 8)), Seq.empty),
  Node(NodeData("another child", List(9, 10, 11, 12)), Seq.empty)
))

val modifiedTree = tree.recMap(
  data => NodeData(
    if(data.text == "parent") "I am the parent!" else "I am a child!",
    data.foo.filter(_ % 2 == 0)
  )
)

println(modifiedTree)

Попробуйте!

Возможно, это то, что вы ищете.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...