Diğer yanıtları tamamlamak için, bazı durumlarda '_' öğesini yer tutucu parametresi olarak kullanırken neden "eksik parametre türünü" aldığınızı gösteren bazı örnekler verilmiştir.
Scala'nın tür çıkarımı, içeriğine dayalı olarak bir ifadenin "beklenen" türünü dikkate alır. Bağlam yoksa, parametrelerin türünü çıkaramaz. Hata iletisinde dikkat edin, _
ilk ve ikinci örnekleri derleyici tarafından oluşturulan tanımlayıcıları x$1
ve x$2
ile değiştirilir.
scala> (_: Int) + (_: Int)
res4: (Int, Int) => Int = <function2>
: Her parametre yer tutucu bir tür yakıştırma ekleyebilir, Alternatif
scala> (_ + _) : ((Int, Int) => Int)
res3: (Int, Int) => Int = <function2>
: tüm ifade bir tür yakıştırma ekleme
scala> _ + _
<console>:5: error: missing parameter type for expanded function ((x$1, x$2) => x$1.$plus(x$2))
_ + _
^
<console>:5: error: missing parameter type for expanded function ((x$1: <error>, x$2) => x$1.$plus(x$2))
_ + _
^
inferencer yardımcı olmak için yeterince bağlam sağlar Sağlanan tip argümanları ile aşağıdaki işlev çağrısında, bağlam benzersizdir ve işlev türü çıkarılır.
scala> def bar[A, R](a1: A, a2: A, f: (A, A) => R) = f(a1, a2)
bar: [A,R](a1: A,a2: A,f: (A, A) => R)R
scala> bar[Int, Int](1, 1, _ + _)
res5: Int = 2
Ancak, başarısız olursa, tip parametrelerini anlaması için derleyici sorarsanız: Biz parametre listelerini currying tarafından olsa da, bunu yardımcı olabilir
scala> bar(1, 1, _ + _)
<console>:7: error: missing parameter type for expanded function ((x$1, x$2) => x$1.$plus(x$2))
bar(1, 1, _ + _)
^
<console>:7: error: missing parameter type for expanded function ((x$1: <error>, x$2) => x$1.$plus(x$2))
bar(1, 1, _ + _)
^
. Burada, (1, 1)
ilk parametre listesine yapılan argümanlar, A
tip parametresinin Int
olması gerektiği sonucunu verir. Daha sonra, f
argümanı türünün (Int, Int) => ?)
olması gerektiğini ve R
dönüş türünün tamsayı eklemenin sonucu olan Int
olduğu sonucuna varır. Standart kütüphanede Traversable.flatMap
'da kullanılan aynı yaklaşımı göreceksiniz.
scala> def foo[A, R](a1: A, a2: A)(f: (A, A) => R) = f(a1, a2)
foo: [A,R](a1: A,a2: A)(f: (A, A) => R)R
scala> foo[Int, Int](1, 1) { _ + _ }
res1: Int = 2
scala> foo(1, 1) { _ + _ }
res0: Int = 2
@Scoobie Bunu güçlendirmek için, alt çizgi Scala'da birçok _different_ amacı için kullanılır. David'in açıkladığı gibi, örneğinizdeki her kullanım aslında farklı bir anlama sahiptir. Scala'da, operatör aşırı yüklenmesinden kaynaklanan sorunların oldukça iyi bir örneği olan başka anlamlar da vardır. İlk başta bununla ilgili sorunlarım varken, dürüstçe düzeltebileceğimi düşündüğümü söyleyebilirim. –