Как пропустить добавление некоторых условий в карте Scala? - PullRequest
5 голосов
/ 27 сентября 2019

У меня есть ситуация, в которой мне нужно создать карту из коллекции, применив фильтр внутри, как показано в коде ниже:

//Say I have a list
//I don't have to apply filter function ...

val myList = List(2,3,4,5)

val evenList = myList.map(x=>{
if ( x is even) x
else 0
}
//And the output is : List(2,0,4,0)
//The output actually needed was List(2,4) without applying filter on top like - ```myList.filter```
//I have objects instead of numbers of a case class so the output becomes :List(object1, None, object2, None)
But actual output needed was : List(object1,object2)

// Обновленный сценарий

val basket = List(2,4,5,6)
case class Apple(name:Option[String],size:Option[Int])

val listApples: List[Apple] = basket.map(x=>{

  val r = new scala.util.Random
  val size = r.nextInt(10)

  if(x%2!=0){
    Apple(None,None)
  }
  else Apple(Some("my-apple"),Some(size))
})

Токовый выход:

Apple(Some(my-apple),Some(2))
Apple(Some(my-apple),Some(0))
Apple(None,None)
Apple(Some(my-apple),Some(4))
Expected was :
Apple(Some(my-apple),Some(2))
Apple(Some(my-apple),Some(0))
Apple(Some(my-apple),Some(4))

Ответы [ 2 ]

5 голосов
/ 27 сентября 2019

Я считаю, collect лучше всего подходит для вашего случая.Он принимает частичную функцию в качестве аргумента, и только если эта функция соответствует, тогда элемент преобразуется и добавляется к результату:

val myList = List(2,3,4,5)

case class Wrapper(i: Int)

val evenList = myList.collect{
  case x if x % 2 == 0 => Wrapper(x)
}

В этом случае только 2 и 4 будут заключены в Wrapper:

List(Wrapper(2), Wrapper(4))
4 голосов
/ 27 сентября 2019

Я не уверен, если я вас правильно понимаю, но почему бы не просто использовать filter непосредственно:

val myList = List(2,3,4,5)

myList.filter(_ % 2 == 0)

Если вы хотите иметь фильтр в качестве функции:

def even(n:Int) = n % 2 == 0

myList.filter(even) 

После обновления вопрос , здесь разница между filter и collect

1015 * Фильтр: 1019

Сбор:

myList
    .collect{ case s if(even(s)) => Apple(Some("my-apple"),Some(s))}

Оба возвращают List(Apple(Some(my-apple),Some(2)), Apple(Some(my-apple),Some(4)))

1028 * Таким образом, единственное отличие состоит в том, что вы можете сделать оба шага сразу с collect.

Однако для меня разделение этих двух шагов в большинстве случаев более читабельно.

...