Aracılığıyla paylaş


Discriminated sendikalar (F#)

Sendikalar discriminated çok sayıda adlandırılmış durumlarda, belki her birinin farklı değerler ve türleri olabilir değerleri için destek sağlar. Discriminated sendikalar heterojen veri için kullanışlıdır; veri geçerli dahil olmak üzere, özel durumlar ve hata durumları olabilir; veri türü bir örnekten diğerine farklılık gösterir; ve küçük nesne hiyerarşisi için alternatif olarak. Buna ek olarak, özyinelemeli discriminated sendikalar ağaç veri yapıları temsil etmek için kullanılır.

type type-name =
   | case-identifier1 [of type1 [ * type2 ...]
   | case-identifier2 [of type3 [ * type4 ...]
   ...

Notlar

Diğer dillerde birleþim türleri discriminated sendikalar benzer, ancak farklılıklar vardır. Olarak bir birleþim türü C++ veya Visual Basic'te bir VARIANT tür değerinde depolanan veriler sabittir değil; farklı seçeneklerden biri olabilir. Diğer dillerde sendikalar, ancak olası seçeneklerin her biri verilen bir büyük bir tanımlayıcı. Büyük/küçük harf tanımlayıcıları çeşitli olası türler nesne türü olan değerlerin adları şunlardır; değerler isteğe bağlıdır. Değerleri yoksa, bir numaralandırma durumda eşdeğer bir durumdur. Değerler varsa, her değeri ya da belirtilen türe veya aynı veya farklı türlerdeki birden çok değer toplayan kayıt düzeni tek bir değer olabilir.

option F# Çekirdek Kitaplığı'nda basit bir discriminated Birliği türüdür. option Türü gibi bildirildi.

// The option type is a discriminated union.
type Option<'a> =
    | Some of 'a
    | None

Önceki kod belirleyen tür Option iki durumda olan bir discriminated Birliği ise Some ve None. Some Durumda olan türü parametresi tarafından gösterilen ilişkili değeri 'a. None Servis talebi ilişkilendirilmiş değere sahiptir. Bu nedenle option ya da bazı tür ya da hiç değer bir değere sahip bir genel tür türünü belirtir. Türü Option de küçük türü diğer adı olan option, yani daha yaygın olarak kullanılır.

Büyük/küçük harf tanımlayıcıları Kurucular discriminated birleşim türü için kullanılabilir. Örneğin, aşağıdaki kod değerleri oluşturmak için kullanılan option türü.

let myOption1 = Some(10.0)
let myOption2 = Some("string")
let myOption3 = None

Büyük/küçük harf tanımlayıcıları ifadelerde eşleşme deseni de kullanılır. İfadenin eşleşen bir desende tanımlayıcıları için tek tek servis talepleriyle ilişkili değerler sağlanır. Örneğin, aşağıdaki kodda, x tanımlayıcısı ile ilişkili değer verilen Some , büyük option türü.

let printValue opt =
    match opt with
    | Some x -> printfn "%A" x
    | None -> printfn "No value."

Normal olarak, büyük/küçük harf tanımlayıcıları sendikanın adını nitelemek olmadan kullanılabilir. Adı sendikanın adını her zaman tam isterseniz uygulayabilirsiniz RequireQualifiedAccess özniteliği için birleşim türünün tanımı.

Discriminated sendikalar kullanarak yerine nesne hiyerarşisi

Discriminated Birliği, küçük nesne hiyerarşisi daha basit bir alternatifi olarak sık sık kullanabilirsiniz. Örneğin, aşağıdaki discriminated Birliği yerine kullanılabilecek bir Shape taban daire, türleri türetilmiş square, vb. sınıfı.

type Shape =
  // The value here is the radius.
| Circle of float
  // The value here is the side length.
| EquilateralTriangle of double
  // The value here is the side length.
| Square of double
  // The values here are the height and width.
| Rectangle of double * double

Bunun yerine bir alanı veya çevre hesaplamak için sanal bir yöntem, gibi bir nesne yönelimli uygulamasında kullanacağınız, bu miktarlar hesaplamak için desen eşleştirme uygun formüller şube için kullanabilirsiniz. Aşağıdaki örnekte, farklı formüller şekli bağlı alanı hesaplamak için kullanılır.

let pi = 3.141592654

let area myShape =
    match myShape with
    | Circle radius -> pi * radius * radius
    | EquilateralTriangle s -> (sqrt 3.0) / 4.0 * s * s
    | Square s -> s * s
    | Rectangle (h, w) -> h * w

let radius = 15.0
let myCircle = Circle(radius)
printfn "Area of circle that has radius %f: %f" radius (area myCircle)

let squareSide = 10.0
let mySquare = Square(squareSide)
printfn "Area of square that has side %f: %f" squareSide (area mySquare)

let height, width = 5.0, 10.0
let myRectangle = Rectangle(height, width)
printfn "Area of rectangle that has height %f and width %f is %f" height width (area myRectangle)

Çıktı aşağıdaki gibidir:

Area of circle that has radius 15.000000: 706.858347
Area of square that has side 10.000000: 100.000000
Area of rectangle that has height 5.000000 and width 10.000000 is 50.000000

Discriminated sendikalar ağaç veri yapıları için kullanma

Discriminated sendikalar Birliği bir veya daha fazla servis taleplerini yazıyla eklenmesi anlamına gelen özyinelemeli olabilir. Özyinelemeli discriminated sendikalar programlama dillerindeki modeli ifadeler için kullanılan ağaç yapıları oluşturmak için kullanılabilir. Aşağıdaki kodda bir özyinelemeli discriminated Birliği bir ikili aðaç veri yapısı oluşturmak için kullanılır. Birleşim, iki durum oluşur Node, bir tamsayı değeri ve sol ve sağ alt ağaç düğümüyle olduğu ve Tip, ağaç sonlandırır.

type Tree =
    | Tip
    | Node of int * Tree * Tree

let rec sumTree tree =
    match tree with
    | Tip -> 0
    | Node(value, left, right) ->
        value + sumTree(left) + sumTree(right)
let myTree = Node(0, Node(1, Node(2, Tip, Tip), Node(3, Tip, Tip)), Node(4, Tip, Tip))
let resultSumTree = sumTree myTree

Önceki kodda, resultSumTree 10 değerine sahiptir. Aşağıdaki resimde için ağaç yapısını gösterir myTree.

MyTree ağaç yapısı

Ayrılmış birleşimler için ağaç diyagramı

Ağaçtaki düğümler de heterojen olması durumunda discriminated sendikalar çalışır. Aşağıdaki kodda, bir tür Expression soyut sözdizimi ağacı bir ifadenin eklenmesini destekler basit bir programlama dili ve çarpma numaralarını ve değişkenleri temsil eder. Özyinelemeli değildir ve ya da sayıları temsil eden bazı sendika taleplerinin (Number) veya değişken (Variable). Diğer durumlarda yinelenen olan ve işlemleri temsil eder (Add ve Multiply), işlenen ifadeler de nerede. Evaluate İşlevini kullanan bir eþleþme deyimine yinelemeli işlem sözdizimi ağacı.

type Expression = 
    | Number of int
    | Add of Expression * Expression
    | Multiply of Expression * Expression
    | Variable of string

let rec Evaluate (env:Map<string,int>) exp = 
    match exp with
    | Number n -> n
    | Add (x, y) -> Evaluate env x + Evaluate env y
    | Multiply (x, y) -> Evaluate env x * Evaluate env y
    | Variable id    -> env.[id]

let environment = Map.ofList [ "a", 1 ;
                               "b", 2 ;
                               "c", 3 ]

// Create an expression tree that represents
// the expression: a + 2 * b.
let expressionTree1 = Add(Variable "a", Multiply(Number 2, Variable "b"))

// Evaluate the expression a + 2 * b, given the
// table of values for the variables.
let result = Evaluate environment expressionTree1

Ne zaman bu kodu yürütüldüğünde, değeri result 5'tir.

Ayrıca bkz.

Diğer Kaynaklar

F# dil başvurusu