Я видел во многих примерах, что иногда используется Seq, а в других случаях List...
Есть ли какая-то разница, отличная от прежней, которая является типом Scala и списком, исходящим из Java?
Я видел во многих примерах, что иногда используется Seq, а в других случаях List...
Есть ли какая-то разница, отличная от прежней, которая является типом Scala и списком, исходящим из Java?
В терминах Java Scala Seq
будет Java List
, а Scala List
будет Java LinkedList
.
Обратите внимание, что Seq
- это trait
, что эквивалентно Java interface
, но с эквивалентом методов защиты вверх и вниз. Scala List
- абстрактный класс, который расширяется Nil
и ::
, которые являются конкретными реализациями List
.
Итак, где Java List
является interface
, Scala List
является реализацией.
Кроме того, Scala List
является неизменным, что не относится к LinkedList
. Фактически, Java не имеет эквивалента неизменяемым коллекциям (только для чтения только гарантирует, что новый объект не может быть изменен, но вы все равно можете изменить старый и, следовательно, "только для чтения" ).
Scala List
сильно оптимизирован компилятором и библиотеками, а это фундаментальный тип данных в функциональном программировании. Однако он имеет ограничения и неадекватен для параллельного программирования. В наши дни Vector
- лучший выбор, чем List
, но привычка трудно сломать.
Seq
- хорошее обобщение для последовательностей, поэтому, если вы программируете на интерфейсы, вы должны использовать это. Обратите внимание, что на самом деле их три: collection.Seq
, collection.mutable.Seq
и collection.immutable.Seq
, а последний - это "по умолчанию", импортированный в область видимости.
Там также GenSeq
и ParSeq
. Последние методы выполняются параллельно, где это возможно, причем первое является родительским для Seq
и ParSeq
обоих, являясь подходящим обобщением, когда parallelism кода не имеет значения. Они оба относительно недавно введены, поэтому люди пока не используют их много.
В Scala список наследуется от Seq, но реализует Product; вот правильное определение List:
sealed abstract class List[+A] extends AbstractSeq[A] with Product with ...
[Примечание: фактическое определение немного сложнее, чтобы вписаться и использовать Scala очень мощная структура коллекции.]
A Seq является Iterable, который имеет определенный порядок элементов. Последовательности предоставляют метод apply()
для индексирования в диапазоне от 0 до длины последовательности. Seq имеет много подклассов, включая Queue, Range, List, Stack и LinkedList.
A List - это Seq, который реализуется как непреложный связанный список. Он лучше всего используется в случаях с шаблонами доступа с последним входом (LIFO).
Seq
- это признак, реализуемый List
.
Если вы определяете свой контейнер как Seq
, вы можете использовать любой контейнер, который реализует свойство Seq
.
scala> def sumUp(s: Seq[Int]): Int = { s.sum }
sumUp: (s: Seq[Int])Int
scala> sumUp(List(1,2,3))
res41: Int = 6
scala> sumUp(Vector(1,2,3))
res42: Int = 6
scala> sumUp(Seq(1,2,3))
res44: Int = 6
Обратите внимание, что
scala> val a = Seq(1,2,3)
a: Seq[Int] = List(1, 2, 3)
Это всего лишь короткая рука для:
scala> val a: Seq[Int] = List(1,2,3)
a: Seq[Int] = List(1, 2, 3)
если тип контейнера не указан, базовая структура данных по умолчанию равна List
.