Как я сортирую массив в Scala?

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

80
задан Peter Mortensen 16 June 2013 в 11:51
поделиться

4 ответа

Sorting.quickSort объявляет функции для получения массива чисел или строк, но я ' м, если вы имеете в виду, что хотите отсортировать список объектов ваших собственных классов?

Я думаю, вы смотрите на функцию

quickSort [K](a : Array[K])(implicit view$1 : (K) => Ordered[K]) : Unit

Что, если я правильно это понимаю, означает, что объекты в массиве должен иметь черту Упорядоченный . Итак, ваш класс должен расширять Ordered (или должен смешивать его) и, следовательно, должен реализовывать метод compare этой черты.

Итак, чтобы скопировать пример из книги:

class MyClass(n: Int) extends Ordered[MyClass] {
   ...
  def compare(that: MyClass) =
    this.n - that.n
}

Итак, для массива [MyClass] должен работать Sorting.quickSort.

32
ответ дан 24 November 2019 в 09:48
поделиться

Если вы просто хотите отсортировать вещи, но не связаны, в частности, с объектом Sorting, вы можете использовать метод сортировки List. Он принимает функцию сравнения в качестве аргумента, поэтому вы можете использовать ее с любыми типами:

List("Steve", "Tom", "John", "Bob").sort((e1, e2) => (e1 compareTo e2) < 0)

List(1, 4, 3, 2).sort((e1, e2) => (e1 < e2))

Списки, вероятно, квалифицируются как «более масштабные», чем массивы.

Из scala api docs :

def sort (lt: (A, A) => Boolean): Список [A]

 Сортировать список в соответствии с функцией сравнения <(e1: a, e2: a) =>

Логическое значение, которое должно быть истинным, если и только если e1 меньше, чем e2.

19
ответ дан 24 November 2019 в 09:48
поделиться
val array = Array((for(i <- 0 to 10) yield scala.util.Random.nextInt): _*)
scala.util.Sorting.quickSort(array)

Массив Scala "по умолчанию" - это изменяемая структура данных, очень близкая к массиву Java. Вообще говоря, это означает, что «массив» не очень похож на Scala, даже если речь идет о изменяемых структурах данных. Однако это служит определенной цели. Если массив - это правильный тип данных для ваших нужд, то вот как вы его сортируете. Между прочим, существуют и другие методы сортировки для Сортировки объектов.

Думаю, я только что понял, в чем ваш вопрос ... вам не нужно передавать какой-либо неявный параметр (в конце концов, он неявный). Этот параметр существует, чтобы сказать, что должен быть какой-то способ преобразовать тип K в упорядоченный [K]. Эти определения уже существуют для классов Scala, поэтому они вам не нужны.

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

scala> case class Person(name: String)
defined class Person

scala> val array = Array(Person("John"), Person("Mike"), Person("Abe"))
array: Array[Person] = Array(Person(John), Person(Mike), Person(Abe))

scala> scala.util.Sorting.quickSort(array)
<console>:11: error: no implicit argument matching parameter type (Person) => Ordered[Person] was found.
       scala.util.Sorting.quickSort(array)
                                   ^
scala> class OrderedPerson(val person: Person) extends Ordered[Person] {
     | def compare(that: Person) = person.name.compare(that.name)
     | }
defined class OrderedPerson

scala> implicit def personToOrdered(p: Person) = new OrderedPerson(p)
personToOrdered: (p: Person)OrderedPerson

scala> scala.util.Sorting.quickSort(array)

scala> array
res8: Array[Person] = Array(Person(Abe), Person(John), Person(Mike))

Теперь, если бы Person был заказан с самого начала, это не было бы проблемой :

scala> case class Person(name: String) extends Ordered[Person] {
     | def compare(that: Person) = name.compare(that.name)
     | }
defined class Person

scala> val array = Array(Person("John"), Person("Mike"), Person("Abe"))
array: Array[Person] = Array(Person(John), Person(Mike), Person(Abe))

scala>  scala.util.Sorting.quickSort(array)

scala> array
res10: Array[Person] = Array(Person(Abe), Person(John), Person(Mike))
5
ответ дан 24 November 2019 в 09:48
поделиться

Хотя принятый ответ не является неправильным, метод быстрой сортировки обеспечивает большую гибкость, чем этот. Я написал этот пример для вас.

import System.out.println
import scala.util.Sorting.quickSort

class Foo(x:Int) {
def get = x
}

//a wrapper around Foo that implements Ordered[Foo]
class OrdFoo(x:Foo) extends Ordered[Foo] {
def compare(that:Foo) = x.get-that.get
}
//another wrapper around Foo that implements Ordered[Foo] in a different way
class OrdFoo2(x:Foo) extends Ordered[Foo] {
def compare(that:Foo) = that.get-x.get
}
//an implicit conversion from Foo to OrdFoo
implicit def convert(a:Foo) = new OrdFoo(a)

//an array of Foos
val arr = Array(new Foo(2),new Foo(3),new Foo(1))

//sorting using OrdFoo
scala.util.Sorting.quickSort(arr)
arr foreach (a=>println(a.get))
/*
This will print:
1
2
3
*/

//sorting using OrdFoo2
scala.util.Sorting.quickSort(arr)(new OrdFoo2(_))
arr foreach (a=>println(a.get))
/*
This will print:
3
2
1
*/

Он показывает, как неявные и явные преобразования из Foo в некоторый класс, расширяющий Ordered [Foo], могут использоваться для получения различных порядков сортировки.

3
ответ дан 24 November 2019 в 09:48
поделиться
Другие вопросы по тегам:

Похожие вопросы: