2016-02-03 15 views
5

aşağıdaki türleri vardır:F # Tipi Kısıtlama uyuşmazlığı genel fonksiyonu üzerine bir sınırlama kullanarak bir f # projesinde

type A = { Name: string } 
type B = { Name: string; SurName: string } 
type C = { Name: string; SurName: string; MaidenName: string } 

ve jenerik argüman üzerinde bir sınırlama kullanarak aşağıdaki işlevi:

let inline filterByName<'a when 'a: (member Name: string)> (name: string) (collection: 'a seq) = 
    collection |> Seq.where(fun i -> i.Name = name) 

Type constraint mismatch. The type

'a

is not compatible with type

C

The type ''a' does not match the type 'C'

Çıkarma:

sorun şu derleme zamanı hatası alıyorum edilir fonksiyon tanımındanbana aşağıdaki derleme zamanı hatası veriyor:

This code is not sufficiently generic. the type variable ^a when ^a:(member get_Name: ^a -> string) could not be generalized because it would escape its scope.

Ne elde etmek çalışıyorum bu durumda, belirli bir ismin bir özelliğiyle "Ad" genel bir tür alır bir işlevi olması. Neyi yanlış yapıyorum ya da neyi özlüyorum?

cevap

5

Sorun, kısıtlanmış üyeyi nasıl çağırıyorsunuzdur - i.Name sözdizimini kullanamazsınız, ancak bunun yerine daha ayrıntılı bir sözdizimi kullanmalısınız. yerine ayrıca bir statik çözülmüş tip değişkeni (^a) kullanmanız gerektiğini

let inline filterByName name collection = 
    collection |> Seq.where(fun i -> (^a : (member Name : string) i) = name) 

Not: Parlak tarafında, bu yöntemin kendisinin imzası çıkarılabilir, bu yüzden her şeyi çoğaltmak gerekmez sağlar normal jenerik tip değişkeni ('a).

+0

harika, teşekkürler dostum –