Scala의 옵션 이해
이 기사에서는 Scala에서 선택적 데이터 요소를 사용하는 방법을 배웁니다. Scala의 Options는 강력한 코드를 작성하는 데 도움이 됩니다.
Scala의 Option 유형
스칼라에서 Option[T]는 주어진 유형의 값을 0개 또는 1개 저장하는 컨테이너입니다. Scala의 Option을 사용하여 선택적 값을 관리하면 두 가지를 보장할 수 있습니다.
- 유형 안전성: 선택적 값을 매개변수화할 수 있습니다.
- 기능적 인식:
option유형은 프로그램에서 더 적은 수의 버그가 생성되도록 하는 많은 기능적 기능을 제공합니다.
스칼라에서 Option[T]는 Some[T] 또는 None[T] 객체로 표현됩니다. 여기 scala.Option은 추상적이고 확장된 기본 클래스이므로 Scala의 Option은 컨테이너처럼 작동합니다.
Option 클래스와 그 하위 클래스에는 구체적인 유형이 필요하다는 것을 기억하십시오. 다음 구문과 같이 명시적이거나 유추될 수 있습니다.
예시:
val obj1: Option[Int] = None
val obj2 = Some(100)
여기서 obj1과 obj2는 Option[Int]의 객체입니다. 한 가지 일반적인 질문은 Option이 Some인지 None인지 확인하는 방법입니다.
이 문제를 해결하기 위해 다음과 같은 기능이 있습니다.
isEmpty: 이 메서드는 개체가None인 경우true를 반환합니다.nonEmpty: 이 메소드는 객체가Some이면true를 반환합니다.isDefined: 이 메소드는 객체가Some이면true를 반환합니다.
Scala에서 Option의 값 검색
get 메소드를 사용하여 Options 값을 검색할 수 있습니다. get 메소드가 None 객체에 대해 호출되면 NoSuchElementException이 발생하며 성공 편향이라고도 합니다.
예제 코드:
val obj1: Option[Int]= ...
val v1 = if (obj1.isDefined)
{
obj1.get
}
else
{
0
}
위의 코드는 패턴 일치를 사용하여 작성할 수도 있습니다.
예제 코드:
val obj1: Option[Int]= ...
val v1 = obj1 match {
case Some(temp) =>
temp
case None =>
0
}
값을 검색하는 getOrElse 및 orElse와 같은 다른 방법도 있습니다.
getOrElse: 이 메소드는 객체가Some인 경우 값을 검색합니다. 그렇지 않으면 기본값을 반환합니다.orElse: 이 메서드는 개체가Some인 경우 값을 검색합니다. 그렇지 않으면alternate옵션을 반환합니다.
선택적 값이 설정되지 않은 경우 getOrElse 메서드는 기본값을 반환할 수 있으므로 매우 유용합니다.
통사론:
val v1 = obj1.getOrElse(0)
Scala의 컨테이너로서의 Option
Option이 Scala에서 다른 값에 대한 컨테이너임을 보았듯이 List를 비슷하게 탐색하는 것처럼 Option을 탐색할 수 있습니다.
이 컨테이너에 대한 몇 가지 메서드를 살펴보겠습니다. Scala의 Option.map 메소드 구문:
final def map[Y](f: (X) => Y): Option[Y]
예제 코드:
val obj1: Option[Int] = Some(100)
assert(obj1.map(_.toString).contains("100"))
assert(obj1.map(_ * 2.0).contains(200))
val obj2: Option[Int] = None
assert(obj2.map(_.toString).isEmpty)
위의 예에서는 Option.map 메소드를 사용하여 포함된 값을 다른 유형으로 변환했습니다. Option.map 방법은 프로그램의 흐름 제어에 영향을 주기 위해 사용될 수도 있습니다.
예제 코드:
val obj1: Option[Int] = Some(10)
val obj2: Option[Int] = None
def mul(n: Int): Int = n * 2
assert(obj1.map(mul).contains(20))
assert(obj2.map(mul).isEmpty)
여기에서 Option[Int]의 두 개체를 만들었습니다. 첫 번째 개체는 10 값을 갖고 두 번째 개체는 비어 있습니다. 그런 다음 입력에 2를 곱하는 mul 메서드를 정의했습니다.
마지막으로 mul 방법을 사용하여 obj1과 obj2를 매핑합니다. obj1 매핑은 Some(20)을 제공하고 obj2 매핑은 None을 제공합니다.
여기서 관찰해야 할 한 가지는 두 번째 호출인 obj2.map(mul)에서 mul 메서드가 전혀 호출되지 않는다는 것입니다. 필터링으로 흐름 제어도 할 수 있습니다.
이를 위한 많은 방법이 있습니다.
filter:Options값이Some이고 제공된 함수가true를 반환하는 경우 이 메서드는Option을 반환합니다.exists: 이 메서드는Option이 설정되고 제공된 함수가true를 반환하는 경우true를 반환합니다.forall:exists메소드와 동일하게 동작합니다.
이러한 기능을 사용하여 코드를 매우 간결하게 작성할 수 있습니다.
가장 높은 점수를 받은 팀을 찾는 예를 들어보겠습니다.
예제 코드:
def highScoringTeam(playerA: Player, playerB: Player, tournament: Tournament): Option[(Player, Int)] =
{ getTopScore(playerA, tournament).foldRight(getTopScore(playerB, tournament)) {
case (playerAInfo, playerBInfo) => playerBInfo.filter {
case (_, scoreB) => scoreB > playerAInfo._2
}.orElse(Some(playerAInfo))
}
}
위의 코드에서 Options를 컬렉션으로 사용할 수 있다는 점을 활용했습니다. 유일한 차이점은 Option은 최대 하나의 값을 가질 수 있다는 것입니다.
