簡體   English   中英

Scala的“案例類”中的“案例”一詞是什么意思?

[英]What is the meaning of the word “case” in scala's “case class”?

我知道case class會導致編譯器增加一個帶有樣板的class ,以實現某種有用的模式(“ 純且不可變的數據保存對象應完全依賴於其構造函數參數 ”)。

但是在這種情況下,“案例”一詞本身對我沒有任何意義。 我習慣於將它用作C#中switch語句的一部分,但這似乎與Scala對該詞的使用無關。

當我可以將單詞附加到特定含義時,我發現更容易編程。 現在我的思維模型是case => boilerplate ,就像blurg => boilerplate 這是一種可行的思維模式,但是模棱兩可讓人們容易誤解或完全忘記。

那么, case一詞與編譯器實際做什么有什么關系?

我不是在尋找“設計師的想法”,而是在給定語言設計常識的前提下,“將這個術語與其含義聯系起來的一種合理方法”。

在我看來,“ case一詞來自案例分析 ,這是一種通過稱為代數數據類型的特殊結構實現的推理技術。 case case class本身可能沒有多大意義,但是當它構成sealed結構的一部分時,例如,Scala就是這樣定義ADT的

sealed trait Number
case object Zero extends Number
case class Succ(v: Number) extends Number

然后我們看到有兩種構造Number形式 ,即使用ZeroSucc 構造函數 因此,無論何時我們必須考慮Number ,我們至少知道要考慮兩種不同的case 例如,假設我們要在Number上定義加法,那么其定義將必須處理兩種情況,例如

def sum(a: Number, b: Number): Number =
  a match {
    case Zero => b
    case Succ(v) => Succ(sum(v, b))
  }

哪里

sum(Succ(Zero), Succ(Zero)) == Succ(Succ(Zero)) // 1 + 1 = 2
sum(Succ(Succ(Zero)), Succ(Zero)) == Succ(Succ(Succ(Zero))) // 2 + 1 = 3
sum(Succ(Zero), Succ(Succ(Zero))) == Succ(Succ(Succ(Zero))) // 1 + 2 = 3
sum(Zero, Succ(Succ(Zero))) == Succ(Succ(Zero)) // 0 + 2 = 2
sum(Succ(Succ(Zero)), Zero) == Succ(Succ(Zero)) // 2 + 0 = 2

請注意,為了定義ADT,Scala如何使用classobjecttrait等術語,這些術語似乎來自於面向對象的范例,但是ADT從概念上講與OO中的類層次結構幾乎沒有共通之處。 我個人覺得這很令人困惑,但是我們必須記住Scala既是功能語言又是OO語言,這可能是造成此類術語溢出的原因。 在其他一些“純”語言中,ADT的case class僅由豎線表示| ,像這樣說

Inductive nat : Type :=
   | O : nat
   | S : nat -> nat.

我的建議是盡量不要成為“言語的奴隸”,而是言語應該為您服務。 重要的是單詞或術語背后的含義 ,而不是單詞本身。 不要圍繞術語構建思維模型,而應圍繞它們為穿越溝通薄弱而努力奮斗的沉重概念構建思維模型。 我認為,正在嘗試進行通信的概念case是ADT。

C#具有switch / case語言功能,該功能允許通過將輸入與一組可能的值進行匹配來控制程序流程。

public static GetEmail(string name)
{
  switch (name)
  {
    case "bill":
      return "bill@example.com";
    case "jane":
      return "jane@example.com";
    default:
      return null;
  }
}

在此, case大致是指“在給定值等於該值的情況下,執行X”。

Scala的match / case功能類似於C#的功能。

def getEmail(name: String): Option[String] = {
  name match {
    case "bill" => Option("bill@example.com")
    case "jane" => Option("jane@example.com")
    case _ => None
  }
}

但這要強大得多。 它旨在針對比字符串更復雜的事物評估“匹配”。 要利用此強大的匹配功能,您可以使用case class定義不可變的數據保存case class

這是一個簡單但希望有用的案例類示例及其與match / case

case class Person(name: String, hasEmail: Boolean)

object EmailHelper {
  def getEmail(person: Person): Option[String] = {
    person match {
      case Person(_, false) => None
      case Person("bill", true) => Option("bill@example.com")
      case Person("jane", true) => Option("jane@example.com")
      case _ => None
    }
  }
}

簡而言之, case class強制執行一組約束,這些約束使該類可與match / case

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM