В Scala.js, как бы вы пересекали графы объектов навигационно? - PullRequest
0 голосов
/ 03 марта 2019

Предположим, что вы хотите пройти по графу объектов навигационным способом , аналогично тому, как мы просматриваем файловые системы.

Например, представьте, что у вас есть граф объектов, который поддерживает этовыражение:

var x = objName.foo.bar.baz.fieldName

Мы можем закодировать это выражение доступа к данным в виде пути следующим образом:

"objName/foo/bar/baz/fieldName"

Разбивая этот путь на сегменты, мы можем легко пройтиграф объектов в JavaScript, потому что в дополнение к традиционной точечной нотации он также поддерживает нотацию доступа к массиву: objName["foo"]["bar"]["baz"]["fieldName"].

В Java или JVM Scala мы можем использовать отражение для обхода графов объектов, но каквы следуете по этим путям для прохождения графов объектов объектов Scala в среде Scala.js?

Другими словами, при заданном пути, похожем по форме на URI, как вы будете проходить через объекты Scala.js, иполя

1 Ответ

0 голосов
/ 10 апреля 2019

Вы наверняка могли бы использовать макрос для преобразования постоянного представления String в метод доступа во время компиляции, но я думаю, вы хотите сделать это во время выполнения для произвольных строк.

Если цель состоит в том, чтобы обойти частично построенные пути, то это просто вопрос, которым вы обмениваетесь функциями доступа.Вы можете использовать что-то вроде этого, чтобы сделать его красивее:

class Path[+A](private val value: () => A) {
  def resolve: A = value()
  def /[B](f: A => B): Path[B] = new Path(() => f(resolve))
}

implicit class PathSyntax[A](val a: A) extends AnyVal {
  def /[B](f: A => B): Path[B] = new Path(() => a) / f
}


object Foo {
  val bar = Bar
}

object Bar {
  val baz = Baz
}

object Baz

Синтаксис не такой красивый, но теперь он безопасен для типов и выглядит не так уж плохо:

val barPath: Path[Bar.type] = Foo / (_.bar)
val bazPath: Path[Baz.type] = barPath / (_.baz)

Против,это потребует больше работы, например.нет правильного равенства / сравнения между Paths.

Если вы хотите придерживаться вашего подхода, я не знаю о прямом решении.Однако я бы сказал, что весь смысл использования ScalaJS состоит в том, чтобы сохранять строгие типы и избегать любых шаблонов, которые могли бы привести к ошибкам во время выполнения, которые компилятор мог бы предотвратить, если бы вы позволили ему выполнить свою работу.

...