Aracılığıyla paylaş


Aşırı Yüklenmiş Yöntem Çözümlemesi

Uygulamada, aşırı yükleme çözümlemesini belirleme kuralları, sağlanan gerçek bağımsız değişkenlere "en yakın" aşırı yüklemeyi bulmaya yöneliktir. Parametre türleri bağımsız değişken türleriyle eşleşen bir yöntem varsa, bu yöntem açıkça en yakın yöntemdir. Bunu engellerseniz, tüm parametre türleri diğer yöntemin parametre türlerinden daha dar (veya aynı) ise bir yöntem diğerinden daha yakın olur. Hiçbir yöntemin parametresi diğerinden daha dar değilse, hangi yöntemin bağımsız değişkenlere daha yakın olduğunu belirlemenin bir yolu yoktur.

Not. Aşırı yükleme çözümlemesi yöntemin beklenen dönüş türünü dikkate almaz.

Ayrıca, adlandırılmış parametre söz dizimi nedeniyle gerçek ve resmi parametrelerin sıralamasının aynı olmayabileceğini unutmayın.

Bir yöntem grubu verildiğinde, bağımsız değişken listesi için gruptaki en uygun yöntem aşağıdaki adımlar kullanılarak belirlenir. Belirli bir adımı uyguladıktan sonra kümede hiçbir üye kalmazsa derleme zamanı hatası oluşur. Kümede yalnızca bir üye kalırsa, bu üye en uygun üyedir. Adımlar şunlardır:

  1. İlk olarak, hiçbir tür bağımsız değişkeni sağlanmamışsa, tür parametreleri olan herhangi bir yönteme tür çıkarımı uygulayın. Bir yöntem için tür çıkarımı başarılı olursa, bu belirli bir yöntem için çıkarsanan tür bağımsız değişkenleri kullanılır. Bir yöntem için tür çıkarımı başarısız olursa, bu yöntem kümeden ortadan kalkar.

  2. Ardından, erişilemeyen veya uygulanamaz olan kümedeki tüm üyeleri ( Bağımsız Değişken Listesine Bölüm Uygulanabilirliği) bağımsız değişken listesine kaldırın

  3. Ardından, bir veya daha fazla bağımsız değişken AddressOf veya lambda ifadesiyse, aşağıdaki gibi her bağımsız değişken için temsilci gevşeme düzeylerini hesaplayın. içindeki en kötü (en düşük) temsilci gevşeme düzeyi, içindeki NMen düşük temsilci gevşeme düzeyinden daha kötüyse, kümeden kaldırın N . Temsilci rahatlama düzeyleri aşağıdaki gibidir:

    1. Hata temsilcisi gevşeme düzeyi : AddressOf veya lambda temsilci türüne dönüştürülemiyorsa.

    2. Dönüş türünün veya parametrelerin daraltılması - bağımsız değişken AddressOf veya bildirilen türe sahip bir lambda ise ve dönüş türünden temsilci dönüş türüne dönüştürme daralıyorsa veya bağımsız değişken normal bir lambda ise ve döndürülen ifadelerinden herhangi birinden temsilci dönüş türüne dönüştürme daraltılıyorsa, veya bağımsız değişken zaman uyumsuz bir lambda ise ve temsilci dönüş türü ise Task(Of T) ve dönüş ifadelerinden T herhangi birinden dönüştürme daraltılıyorsa veya bağımsız değişken yineleyici lambda ise ve temsilci dönüş türü IEnumerator(Of T) veya IEnumerable(Of T) verim işlenenlerinden T herhangi birinden dönüştürme daraltılıyorsa.

    3. Temsilci türü System.Delegate veya System.MultiCastDelegateSystem.Objectise, temsilci rahatlamasını imzasız temsilci olarak genişletme.

    4. Bırakma dönüş veya bağımsız değişkenleri temsilci gevşeme -- bağımsız değişken veya AddressOf bildirilen dönüş türüne sahip bir lambda ise ve temsilci türü bir dönüş türü yoksa; ya da bağımsız değişken bir veya daha fazla dönüş ifadesi içeren bir lambda ise ve temsilci türü bir dönüş türü içermiyorsa; ya da bağımsız değişken AddressOf parametresiz veya lambda ise ve temsilci türünde parametreler varsa.

    5. Dönüş türünün genişletilmesi için temsilci gevşetme -- bağımsız değişken AddressOf veya bildirilen dönüş türüne sahip bir lambda ise ve dönüş türünden temsilcinin türüne genişleyen bir dönüştürme varsa; ya da bağımsız değişken, tüm dönüş ifadelerinden temsilci dönüş türüne dönüştürmenin genişletildiği veya en az bir genişletmeye sahip kimliğin olduğu normal bir lambda ise veya bağımsız değişken zaman uyumsuz bir lambda ise ve temsilci Task(Of T) ise veya Task ve tüm dönüş ifadelerinden TObject/sırasıyla en az bir genişletme ile genişletme veya kimlik dönüştürmedir; ya da bağımsız değişken yineleyici lambda ise ve temsilci IEnumerator(Of T) veya IEnumerable(Of T) veya veya IEnumerator ise IEnumerable ve tüm dönüş ifadelerinden T/Object dönüştürme en az bir genişletme ile genişler veya kimliktir.

    6. Kimlik temsilcisi rahatlaması -- bağımsız değişken temsilciyle tam olarak eşleşen bir AddressOf veya lambda ise, parametrelerin genişletilmesi, daraltılması veya bırakılması ya da döndürülmesi ya da veriminin olmaması. Ardından, kümenin bazı üyeleri bağımsız değişkenlerden herhangi birine uygulanacak daraltma dönüştürmeleri gerektirmiyorsa, bunu yapacak tüm üyeleri kaldırın. Örneğin:

    Sub f(x As Object)
    End Sub
    
    Sub f(x As Short)
    End Sub
    
    Sub f(x As Short())
    End Sub
    
    f("5") ' picks the Object overload, since String->Short is narrowing
    f(5)   ' picks the Object overload, since Integer->Short is narrowing
    f({5}) ' picks the Object overload, since Integer->Short is narrowing
    f({})  ' a tie-breaker rule subsequent to [3] picks the Short() overload
    
    
  4. Daha sonra, eleme aşağıdaki gibi daralma temelinde yapılır. (Seçenek Katı Açıksa, daraltma gerektiren tüm üyelerin zaten uygulanabilir olmadığını ( Bölüm Bağımsız Değişken Listesine Uygulanabilirliği) ve 2. Adım tarafından kaldırıldığını unutmayın.)

    1. Kümenin bazı örnek üyeleri yalnızca bağımsız değişken ifade türünün Objectolduğu yerlerde daraltma dönüştürmeleri gerektiriyorsa, diğer tüm üyeleri kaldırın.
    2. Kümede yalnızca öğesinden Objectdaraltma gerektiren birden fazla üye varsa, çağırma hedef ifadesi geç bağlanan yöntem erişimi olarak yeniden sınıflandırılır (ve yöntem grubunu içeren tür bir arabirimse veya geçerli üyelerden biri uzantı üyesiyse bir hata verilir).
    3. Yalnızca sayısal değişmez değerlerden daraltma gerektiren adaylar varsa, aşağıdaki adımlarla kalan tüm adaylar arasında en belirgin olanını seçin. Kazanan yalnızca sayısal değişmez değerlerden daraltma gerektiriyorsa, aşırı yükleme çözümlemesinin sonucu olarak seçilir; aksi takdirde bu bir hatadır.

    Not. Bu kuralın gerekçesi, bir program gevşek türe sahipse (çoğu veya tüm değişkenler olarak Objectbildirilir), birçok dönüştürme Object daraltıldığında aşırı yükleme çözümlemesinin zor olmasıdır. Aşırı yükleme çözümlemesinin birçok durumda başarısız olması (yöntem çağrısına bağımsız değişkenlerin güçlü yazılması gerekir) yerine, çağrıya uygun aşırı yüklenmiş yöntemin çözümlenmesi çalışma süresine kadar ertelenir. Bu, gevşek türdeki çağrının ek atamalar olmadan başarılı olmasını sağlar. Ancak, bunun talihsiz bir yan etkisi, geç bağlı çağrının gerçekleştirilmesi için çağrı hedefinin olarak Objectataması gerekir. Bir yapı değeri söz konusu olduğunda, bu değerin geçici olarak kutulanması gerektiği anlamına gelir. Sonunda çağrılan yöntem yapının bir alanını değiştirmeye çalışırsa, yöntem döndürdüğünde bu değişiklik kaybolur. Geç bağlama her zaman uyguladıkları arabirimlerin üyelerinden farklı adlara sahip olabilecek çalışma zamanı sınıfının veya yapı türünün üyelerine karşı çözümlendiği için arabirimler bu özel kuralın dışında tutulur.

  5. Daha sonra, herhangi bir örnek yöntemi, daraltma gerektirmeyen kümede kalırsa, kümedeki tüm uzantı yöntemlerini ortadan kaldırın. Örneğin:

    Imports System.Runtime.CompilerServices
    
    Class C3
        Sub M1(d As Integer)
        End Sub
    End Class
    
    Module C3Extensions
        <Extension> _
        Sub M1(c3 As C3, c As Long)
        End Sub
    
        <Extension> _
        Sub M1(c3 As C3, c As Short)
        End Sub
    End Module
    
    Module Test
        Sub Main()
            Dim c As New C3()
            Dim sVal As Short = 10
            Dim lVal As Long = 20
    
            ' Calls C3.M1, since C3.M1 is applicable.
            c.M1(sVal)
    
            ' Calls C3Extensions.M1 since C3.M1 requires a narrowing conversion
            c.M1(lVal)
        End Sub
    End Module
    

    Not. İçeri aktarma (kapsama yeni uzantı yöntemleri getirebilir) eklemenin mevcut bir örnek yönteminde bir uzantı yöntemine yeniden bağlanma çağrısına neden olmamasını garanti eden geçerli örnek yöntemleri varsa uzantı yöntemleri yoksayılır. Bazı uzantı yöntemlerinin (arabirimler ve/veya tür parametrelerinde tanımlananlar) geniş kapsamı göz önünde bulundurulduğunda, uzantı yöntemlerine bağlamaya yönelik daha güvenli bir yaklaşımdır.

  6. Ardından, kümenin M ve NM öğesinin herhangi iki üyesi verildiğinde, bağımsız değişken listesinden daha belirgin (bağımsız değişken listesi verilen üyelerin/türlerin Bölüm Özgülüğü) N kümeden kaldırınN. Kümede birden fazla üye kalıyorsa ve bağımsız değişken listesi dikkate alındığında kalan üyeler eşit olarak belirli değilse, derleme zamanı hata sonuçları.

  7. Aksi takdirde, kümenin M ve Nöğesinin iki üyesi göz önünde bulundurulduğunda, aşağıdaki bağlamaya son verme kurallarını sırayla uygulayın:

    1. ParamArray parametresi yoksa M , ancak N bunu yaparsa veya her ikisi de bunu yapar ancak M ParamArray parametresine olduğundan N daha az bağımsız değişken geçirirse, kümeden kaldırın N . Örneğin:

      Module Test
          Sub F(a As Object, ParamArray b As Object())
              Console.WriteLine("F(Object, Object())")
          End Sub
      
          Sub F(a As Object, b As Object, ParamArray c As Object())
              Console.WriteLine("F(Object, Object, Object())")
          End Sub
      
         Sub G(Optional a As Object = Nothing)
            Console.WriteLine("G(Object)")
         End Sub
      
         Sub G(ParamArray a As Object())
            Console.WriteLine("G(Object())")
         End Sub    Sub Main()
              F(1)
              F(1, 2)
              F(1, 2, 3)
            G()
          End Sub
      End Module
      

      Yukarıdaki örnek aşağıdaki çıkışı oluşturur:

      F(Object, Object())
      F(Object, Object, Object())
      F(Object, Object, Object())
      G(Object)
      

      Not. Bir sınıf paramarray parametresine sahip bir yöntem bildirdiğinde, genişletilmiş formlardan bazılarını da normal yöntemler olarak eklemek nadir değildir. Bunu yaptığınızda, paramarray parametresine sahip bir yöntemin genişletilmiş bir biçimi çağrıldığında oluşan bir dizi örneğinin ayrılmasını önlemek mümkündür.

    2. değerinden daha türetilmiş bir türde tanımlanmışsaM, kümesinden kaldırınN.N Örneğin:

      Class Base
          Sub F(Of T, U)(x As T, y As U)
          End Sub
      End Class
      
      Class Derived
          Inherits Base
      
          Overloads Sub F(Of T, U)(x As U, y As T)
          End Sub
      End Class
      
      Module Test
          Sub Main()
              Dim d As New Derived()
      
              ' Calls Derived.F
              d.F(10, 10)
          End Sub
      End Module
      

      Bu kural, uzantı yöntemlerinin tanımlandığı türler için de geçerlidir. Örneğin:

      Imports System.Runtime.CompilerServices
      
      Class Base
      End Class
      
      Class Derived
          Inherits Base
      End Class
      
      Module BaseExt
          <Extension> _
          Sub M(b As Base, x As Integer)
          End Sub
      End Module
      
      Module DerivedExt
          <Extension> _
          Sub M(d As Derived, x As Integer)
          End Sub
      End Module
      
      Module Test
          Sub Main()
              Dim b As New Base()
              Dim d As New Derived()
      
              ' Calls BaseExt.M
              b.M(10)
      
              ' Calls DerivedExt.M 
              d.M(10)
          End Sub
      End Module
      
    3. ve uzantı yöntemleriyse M ve hedef türü M bir sınıf veya yapı ise ve hedef türü N bir arabirimse, kümeden kaldırınN.N Örneğin:

      Imports System.Runtime.CompilerServices
      
      Interface I1
      End Interface
      
      Class C1
          Implements I1
      End Class
      
      Module Ext1
          <Extension> _
          Sub M(i As I1, x As Integer)
          End Sub
      End Module
      
      Module Ext2
          <Extension> _
          Sub M(c As C1, y As Integer)
          End Sub
      End Module
      
      Module Test
          Sub Main()
              Dim c As New C1()
      
              ' Calls Ext2.M, because Ext1.M is hidden since it extends
              ' an interface.
              c.M(10)
      
              ' Calls Ext1.M
              CType(c, I1).M(10)
          End Sub
      End Module
      
    4. ve uzantı yöntemleriyse M ve hedef türü M ve N türü parametre değişiminden sonra aynıysa ve tür parametresi değiştirmesinden önceki hedef türü M tür parametreleri içermiyorsa ancak hedef türüN, hedef türünden Ndaha az tür parametresine sahipse, kümesinden kaldırınN.N Örneğin:

      Imports System.Runtime.CompilerServices
      
      Module Module1
          Sub Main()
              Dim x As Integer = 1
              x.f(1) ' Calls first "f" extension method
      
              Dim y As New Dictionary(Of Integer, Integer)
              y.g(1) ' Ambiguity error
          End Sub
      
          <Extension()> Sub f(x As Integer, z As Integer)
          End Sub
      
          <Extension()> Sub f(Of T)(x As T, z As T)
          End Sub
      
          <Extension()> Sub g(Of T)(y As Dictionary(Of T, Integer), z As T)
          End Sub
      
          <Extension()> Sub g(Of T)(y As Dictionary(Of T, T), z As T)
          End Sub
      End Module
      
    5. Tür bağımsız değişkenleri yerine kullanılmadan önce, değerinden daha az genelseM (Bölüm Genelliği) Nkümeden kaldırınN.

    6. Bir uzantı yöntemi değilse M ve N ise, kümeden kaldırın N .

    7. ve N uzantı yöntemleriyse ve M daha önce N bulunduysa M (Bölüm Uzantısı Yöntemi Koleksiyonu), kümeden kaldırınN. Örneğin:

      Imports System.Runtime.CompilerServices
      
      Class C1
      End Class
      
      Namespace N1
          Module N1C1Extensions
              <Extension> _
              Sub M1(c As C1, x As Integer)
              End Sub
          End Module
      End Namespace
      
      Namespace N1.N2
          Module N2C1Extensions
              <Extension> _
              Sub M1(c As C1, y As Integer)
              End Sub
          End Module
      End Namespace
      
      Namespace N1.N2.N3
          Module Test
              Sub Main()
                  Dim x As New C1()
      
                  ' Calls N2C1Extensions.M1
                  x.M1(10)
              End Sub
          End Module
      End Namespace
      

      Uzantı yöntemleri aynı adımda bulunursa, bu uzantı yöntemleri belirsizdir. Çağrı her zaman uzantı yöntemini içeren standart modülün adı kullanılarak ve normal bir üye gibi uzantı yönteminin çağrılmasıyla kesinleştirilebilir. Örneğin:

      Imports System.Runtime.CompilerServices
      
      Class C1
      End Class
      
      Module C1ExtA
          <Extension> _
          Sub M(c As C1)
          End Sub
      End Module
      
      Module C1ExtB
          <Extension> _
          Sub M(c As C1)
          End Sub
      End Module
      
      Module Main
          Sub Test()
              Dim c As New C1()
      
              C1.M()               ' Ambiguous between C1ExtA.M and BExtB.M
              C1ExtA.M(c)          ' Calls C1ExtA.M
              C1ExtB.M(c)          ' Calls C1ExtB.M
          End Sub
      End Module
      
    8. N Ve her ikisi de tür bağımsız değişkenleri üretmek için tür çıkarımı gerektiriyorsa M ve M türü bağımsız değişkenlerinden herhangi biri için baskın türün belirlenmesini gerektirmediyse (yani, her tür bağımsız değişkeni tek bir türe çıkarılır), ancak N kümeden elendiN.

      Not. Bu kural, önceki sürümlerde başarılı olan aşırı yükleme çözümlemesinin (bir tür bağımsız değişkeni için birden çok tür çıkarılmasının hataya neden olacağı), aynı sonuçları üretmeye devam etmesini sağlar.

    9. Bir ifadeden AddressOf temsilci oluşturma ifadesinin hedefini çözümlemek için aşırı yükleme çözümlemesi yapılıyorsa ve hem temsilci M hem de bir alt yordam olan N işlevlerse, kümeden kaldırın N . Benzer şekilde, hem temsilci hem M de alt yordamsa, N bir işlevse kümeden kaldırın N .

    10. Açık M bağımsız değişkenler yerine herhangi bir isteğe bağlı parametre varsayılanı kullanmadıysa, ama N kullandıysa, kümeden kaldırın N .

    11. Tür bağımsız değişkenleri yerine kullanılmadan önce, değerinden daha fazla genelliğe (Bölüm Genelliği) NsahipseM, kümeden kaldırınN.

  8. Aksi takdirde, çağrı belirsizdir ve derleme zamanı hatası oluşur.

Bağımsız değişken listesi verilen üyelerin/türlerin özgüllüğü

Bir üyeM, bağımsız değişken listesi Averildiğinde, imzaları aynıysa veya içindeki M her parametre türü içindeki Nilgili parametre türüyle aynıysa, ile eşit olarak özelNolarak kabul edilir.

Not. İki üye, uzantı yöntemleri nedeniyle aynı imzaya sahip bir yöntem grubuna bağlanabilir. İki üye de aynı derecede özel olabilir, ancak tür parametreleri veya paramarray genişletmesi nedeniyle aynı imzaya sahip olmayabilir.

Bir üyeM, imzalarının farklı olması ve içindeki M en az bir parametre türünün içindeki Nparametre türünden daha özel olması ve içindeki N hiçbir parametre türünün içindeki parametre türünden Mdaha özel olmamasından daha belirginN olarak kabul edilir. Bir parametre Mj çifti verildiğinde ve Nj bir bağımsız değişkenle Ajeşleşirse, Mj türü, aşağıdaki koşullardan biri doğruysa türünden Njdaha belirgin olarak kabul edilir:

  • türünden türüne Mj bir genişletme dönüştürmesi Njvardır. (Not. Parametre türleri bu durumda gerçek bağımsız değişkene bakılmaksızın karşılaştırıldığından, sabit ifadelerden değerin sığdığı sayısal bir türe genişletme dönüştürmesi bu durumda dikkate alınmaz.)

  • Aj, 0Mj sayısal bir türdür ve Nj numaralandırılmış bir türdür. (Not. Sabit değer 0 herhangi bir numaralandırılmış türe genişletildiğinden bu kural gereklidir. Numaralandırılmış tür, temel alınan türüne genişlediğinden, üzerindeki aşırı yükleme çözümlemesi 0 varsayılan olarak sayısal türler yerine numaralandırılmış türleri tercih eder. Bu davranışın uygun olmadığını belirten birçok geri bildirim aldık.)

  • Mjve Nj hem sayısal türlerdir hem Mj de , , SByte, Short, UShort, , Integer, UInteger, Long, ULong, Decimal, Single, Doublelistesinden Bytedaha erken Nj gelir. (Not. Belirli bir boyuttaki imzalı ve imzasız sayısal türleri arasında yalnızca daraltma dönüştürmeleri olduğundan, sayısal türler hakkındaki kural yararlıdır. Yukarıdaki kural, daha "doğal" sayısal tür yerine iki tür arasındaki bağı keser. Bu özellikle, belirli bir boyutun hem imzalı hem de imzasız sayısal türlerine (örneğin, her ikisine de uyan sayısal değişmez değer) genişleyen bir türde aşırı yükleme çözümlemesi yaparken önemlidir.)

  • Mjve Nj temsilci işlev türleridir ve dönüş türü, lambda yöntemi olarak sınıflandırılırsa Aj ve Mj veya Nj ise dönüş türünden MjNj daha belirgindirSystem.Linq.Expressions.Expression(Of T); ardından türün tür bağımsız değişkeni (temsilci türü olduğu varsayılarak) karşılaştırılan türle değiştirilir.

  • Mj türüyle Ajaynıdır ve Nj aynı değildir. (Not. Önceki kuralın C# kuralından biraz farklı olduğunu, C# değerinin dönüş türlerini karşılaştırmadan önce temsilci işlev türlerinin aynı parametre listelerine sahip olmasını gerektirdiğini, ancak Visual Basic'in bunu gerektirmediğini unutmayın.)

Genellik

Bir üye M aşağıdaki gibi bir üyeden Ndaha az genel olarak belirlenir:

  1. Her eşleşen parametre Mj çifti ve MjNjiçin, yöntemdeki tür parametrelerine göre daha Nj az veya eşit genelse ve yöntemdeki tür parametrelerine göre en az bir Mj tane daha az genelse.
  2. Aksi takdirde, eşleşen her parametre Mj çifti için ve NjMj türündeki tür parametrelerine göre daha Nj az veya eşit genelse ve türündeki tür parametrelerine göre en az bir Mj tane daha az genelse, bundan M daha az genel Nolur.

M Türleri ve Nt her ikisi de tür parametrelerine başvuruda bulunursa Mt veya her ikisi de tür parametrelerine başvurmazsa parametrenin parametre N için eşit genel olduğu kabul edilir. Mbir tür parametresine başvurmazsa ve Nt başvuruda bulunursa Mt değerinden daha N az genel olarak kabul edilir.

Örneğin:

Class C1(Of T)
    Sub S1(Of U)(x As U, y As T)
    End Sub

    Sub S1(Of U)(x As U, y As U)
    End Sub

    Sub S2(x As Integer, y As T)
    End Sub

    Sub S2(x As T, y As T)
    End Sub
End Class

Module Test
    Sub Main()
        Dim x As C1(Of Integer) = New C1(Of Integer)

        x.S1(10, 10)    ' Calls S1(U, T)
        x.S2(10, 10)    ' Calls S2(Integer, T)
    End Sub
End Module

Currying sırasında düzeltilen uzantı yöntemi türü parametreleri, yöntemdeki tür parametreleri değil türündeki tür parametreleri olarak kabul edilir. Örneğin:

Imports System.Runtime.CompilerServices

Module Ext1
    <Extension> _
    Sub M1(Of T, U)(x As T, y As U, z As U)
    End Sub
End Module

Module Ext2
    <Extension> _
    Sub M1(Of T, U)(x As T, y As U, z As T)
    End Sub
End Module

Module Test
    Sub Main()
        Dim i As Integer = 10

        i.M1(10, 10)
    End Sub
End Module

Genellik derinliği

Her eşleşen parametre Mj çifti ve için , değerinden daha büyük veya eşit genellik derinliğine sahipse ve NjMj en az bir Mj tanesinde daha fazla genellik Njderinliği varsa, üyenin genellik derinliği bir üyeden N daha büyük olur.M Genellik derinliği aşağıdaki gibi tanımlanır:

  • Tür parametresi dışındaki her şey, tür parametresinden daha fazla genelliğe sahiptir;

  • Özyinelemeli olarak, en az bir tür bağımsız değişkeninin genellik derinliği daha büyükse ve hiçbir tür bağımsız değişkeni diğerinde karşılık gelen tür bağımsız değişkeninden daha az derinlik içermiyorsa, yapılandırılmış bir tür başka bir türe göre daha fazla genellik derinliğine sahiptir (aynı sayıda tür bağımsız değişkeniyle).

  • Birincinin öğe türü ikincinin öğe türünden daha fazla genelliğe sahipse, dizi türü başka bir dizi türünden (aynı sayıda boyutla) daha fazla genelliğe sahiptir.

Örneğin:

Module Test

    Sub f(Of T)(x As Task(Of T))
    End Sub

    Sub f(Of T)(x As T)
    End Sub

    Sub Main()
        Dim x As Task(Of Integer) = Nothing
        f(x)            ' Calls the first overload
    End Sub
End Module

Bağımsız Değişken Listesine Uygulanabilirlik

Yöntem, bağımsız değişken listeleri kullanılarak çağrılabiliyorsa bir tür bağımsız değişkenleri, konumsal bağımsız değişkenler ve adlandırılmış bağımsız değişkenler kümesi için geçerlidir . Bağımsız değişken listeleri, parametre listelerine karşı aşağıdaki gibi eşleştirilir:

  1. İlk olarak, her konumsal bağımsız değişkeni yöntem parametreleri listesiyle eşleştirin. Parametrelerden daha fazla konumsal bağımsız değişken varsa ve son parametre parametre değilse, yöntem geçerli değildir. Aksi takdirde paramarray parametresi, konumsal bağımsız değişkenlerin sayısıyla eşleşecek şekilde paramarray öğe türünün parametreleriyle genişletilir. Parametreye gidecek bir konumsal bağımsız değişken atlanırsa, yöntem geçerli değildir.
  2. Ardından, her adlandırılmış bağımsız değişkeni verilen adla bir parametreyle eşleştirin. Adlandırılmış bağımsız değişkenlerden biri eşleşmezse, paramarray parametresiyle eşleşirse veya zaten başka bir konumsal veya adlandırılmış bağımsız değişkenle eşleşen bir bağımsız değişkenle eşleşirse, yöntem geçerli değildir.
  3. Ardından, tür bağımsız değişkenleri belirtilmişse, tür parametre listesiyle eşleştirilirler. İki listede aynı sayıda öğe yoksa, tür bağımsız değişken listesi boş olmadığı sürece yöntem geçerli değildir. Tür bağımsız değişken listesi boşsa tür bağımsız değişken listesini denemek ve çıkarabilmek için tür çıkarımı kullanılır. Tür çıkarım başarısız olursa yöntemi geçerli değildir. Aksi takdirde, tür bağımsız değişkenleri imzadaki tür parametrelerinin yerine doldurulur. Eşleşmeyen parametreler isteğe bağlı değilse, yöntemi geçerli değildir.
  4. Bağımsız değişken ifadeleri eşleştikleri parametre türlerine örtük olarak dönüştürülebilir değilse, yöntem geçerli değildir.
  5. Bir parametre ByRef ise ve parametre türünden bağımsız değişkenin türüne örtük bir dönüştürme yoksa, yöntemi geçerli değildir.
  6. Tür bağımsız değişkenleri yöntemin kısıtlamalarını ihlal ederse (3. Adımdaki çıkarımlı tür bağımsız değişkenleri dahil), yöntem geçerli değildir. Örneğin:
Module Module1
    Sub Main()
        f(Of Integer)(New Exception)
        ' picks the first overload (narrowing),
        ' since the second overload (widening) violates constraints 
    End Sub

    Sub f(Of T)(x As IComparable)
    End Sub

    Sub f(Of T As Class)(x As Object)
    End Sub
End Module

Tek bir bağımsız değişken ifadesi bir paramarray parametresiyle eşleşiyorsa ve bağımsız değişken ifadesinin türü hem paramarray parametresinin türüne hem de paramarray öğe türüne dönüştürülebilirse, yöntem iki özel durumla birlikte hem genişletilmiş hem de genişletilmemiş formlarında uygulanabilir. Bağımsız değişken ifadesinin türünden paramarray türüne dönüştürme daraltılıyorsa, yöntem yalnızca genişletilmiş biçiminde uygulanabilir. Bağımsız değişken ifadesi değişmez değer Nothingise, yöntem yalnızca genişletilmemiş biçiminde uygulanabilir. Örneğin:

Module Test
    Sub F(ParamArray a As Object())
        Dim o As Object

        For Each o In a
            Console.Write(o.GetType().FullName)
            Console.Write(" ")
        Next o
        Console.WriteLine()
    End Sub

    Sub Main()
        Dim a As Object() = { 1, "Hello", 123.456 }
        Dim o As Object = a

        F(a)
        F(CType(a, Object))
        F(o)
        F(CType(o, Object()))
    End Sub
End Module

Yukarıdaki örnek aşağıdaki çıkışı oluşturur:

System.Int32 System.String System.Double
System.Object[]
System.Object[]
System.Int32 System.String System.Double

öğesinin ilk ve son çağrılarındaF, bağımsız değişken türünden parametre türüne (her ikisi de türündedirObject()) bir genişletme dönüştürmesi mevcut olduğundan ve bağımsız değişken normal değer parametresi olarak geçirildiğinden normal biçimi F geçerlidir. İkinci ve üçüncü çağrılarda, bağımsız değişken türünden parametre türüne genişletme dönüştürmesi olmadığından normal biçimi F geçerli değildir (dönüştürmeler ObjectObject() daraltmadır). Ancak genişletilmiş biçimi F uygulanabilir ve çağrı tarafından tek öğeli bir öğe Object() oluşturulur. Dizinin tek öğesi verilen bağımsız değişken değeriyle başlatılır (kendisi bir Object()başvurudur).

İsteğe Bağlı Parametreler için Bağımsız Değişkenleri Geçirme ve Bağımsız Değişkenleri Seçme

Parametre bir değer parametresiyse, eşleşen bağımsız değişken ifadesi değer olarak sınıflandırılmalıdır. Değer parametresinin türüne dönüştürülür ve çalışma zamanında parametre olarak geçirilir. Parametre bir başvuru parametresiyse ve eşleşen bağımsız değişken ifadesi türü parametreyle aynı olan bir değişken olarak sınıflandırılırsa, değişken başvurusu çalışma zamanında parametre olarak geçirilir.

Aksi takdirde, eşleşen bağımsız değişken ifadesi değişken, değer veya özellik erişimi olarak sınıflandırılırsa, parametre türünün geçici bir değişkeni ayrılır. Çalışma zamanında yöntem çağırmadan önce, bağımsız değişken ifadesi bir değer olarak yeniden sınıflandırılır, parametrenin türüne dönüştürülür ve geçici değişkene atanır. Ardından geçici değişkene bir başvuru parametresi olarak geçirilir. Yöntem çağrısı değerlendirildikten sonra, bağımsız değişken ifadesi bir değişken veya özellik erişimi olarak sınıflandırılırsa, geçici değişken değişken ifadeye veya özellik erişim ifadesine atanır. Özellik erişim ifadesinde erişimci yoksa Set atama gerçekleştirilmez.

Bağımsız değişkenin sağlanmadığı isteğe bağlı parametreler için derleyici, aşağıda açıklandığı gibi bağımsız değişkenleri seçer. Her durumda, genel tür değiştirmeden sonra parametre türüne göre test eder.

  • İsteğe bağlı parametre özniteliğine System.Runtime.CompilerServices.CallerLineNumbersahipse ve çağrı kaynak kodundaki bir konumdan geliyorsa ve bu konumun satır numarasını temsil eden bir sayısal değişmez değer parametre türüne iç dönüştürmeye sahipse, sayısal değişmez değer kullanılır. Çağırma birden çok satıra yayılıyorsa, kullanılacak satır seçimi uygulamaya bağlıdır.

  • İsteğe bağlı parametre özniteliğine System.Runtime.CompilerServices.CallerFilePathsahipse ve çağrı kaynak kodundaki bir konumdan geliyorsa ve bu konumun dosya yolunu temsil eden bir dize değişmez değeri parametre türüne yönelik bir iç dönüştürmeye sahipse, dize değişmez değeri kullanılır. Dosya yolunun biçimi uygulamaya bağlıdır.

  • İsteğe bağlı parametre özniteliğine System.Runtime.CompilerServices.CallerMemberNamesahipse ve çağrı bir tür üyesinin gövdesinde veya bu tür üyenin herhangi bir bölümüne uygulanmış bir öznitelikteyse ve bu üye adını temsil eden bir dize sabit değeri parametre türüne iç dönüştürmeye sahipse, dize değişmez değeri kullanılır. Özellik erişimcilerinin veya özel olay işleyicilerinin parçası olan çağrılar için, kullanılan üye adı özelliğin veya olayın kendisidir. Bir işlecin veya oluşturucunun parçası olan çağrılar için uygulamaya özgü bir ad kullanılır.

Yukarıdakilerden hiçbiri geçerli değilse isteğe bağlı parametrenin varsayılan değeri kullanılır (veya Nothing varsayılan değer sağlanmadıysa). Yukarıdakilerden birden fazlası geçerliyse, hangisinin kullanılacağı uygulamaya bağlıdır.

CallerLineNumber ve CallerFilePath öznitelikleri günlüğe kaydetme için kullanışlıdır. CallerMemberName, uygulamak INotifyPropertyChangediçin kullanışlıdır. Örnekler aşağıda verilmiştir.

Sub Log(msg As String,
        <CallerFilePath> Optional file As String = Nothing,
        <CallerLineNumber> Optional line As Integer? = Nothing)
    Console.WriteLine("{0}:{1} - {2}", file, line, msg)
End Sub

WriteOnly Property p As Integer
    Set(value As Integer)
        Notify(_p, value)
    End Set
End Property

Private _p As Integer

Sub Notify(Of T As IEquatable(Of T))(ByRef v1 As T, v2 As T,
        <CallerMemberName> Optional prop As String = Nothing)
    If v1 IsNot Nothing AndAlso v1.Equals(v2) Then Return
    If v1 Is Nothing AndAlso v2 Is Nothing Then Return
    v1 = v2
    RaiseEvent PropertyChanged(Me, New PropertyChangedEventArgs(prop))
End Sub

Microsoft Visual Basic, yukarıdaki isteğe bağlı parametrelere ek olarak, meta verilerden (örneğin, bir DLL başvurusundan) içeri aktarıldıysa bazı ek isteğe bağlı parametreleri de tanır:

  • Meta verilerden içeri aktarıldıktan sonra Visual Basic de parametresini parametrenin <Optional> isteğe bağlı olduğunu gösterir: Bu şekilde, anahtar sözcük kullanılarak Optional ifade edilemese de isteğe bağlı parametresi olan ancak varsayılan değeri olmayan bir bildirimi içeri aktarmak mümkündür.

  • İsteğe bağlı parametre özniteliğine Microsoft.VisualBasic.CompilerServices.OptionCompareAttributesahipse ve sayısal değişmez değer 1 veya 0 parametre türüne dönüştürmeye sahipse, derleyici etkinse Option Compare Text değişmez değer 1 veya etkinse Optional Compare Binary değişmez değer 0 bağımsız değişkeni olarak kullanır.

  • İsteğe bağlı parametre özniteliğine System.Runtime.CompilerServices.IDispatchConstantAttributesahipse ve türündeyse Objectve varsayılan bir değer belirtmiyorsa, derleyici bağımsız değişkenini New System.Runtime.InteropServices.DispatchWrapper(Nothing)kullanır.

  • İsteğe bağlı parametre özniteliğine System.Runtime.CompilerServices.IUnknownConstantAttributesahipse ve türündeyse Objectve varsayılan bir değer belirtmiyorsa, derleyici bağımsız değişkenini New System.Runtime.InteropServices.UnknownWrapper(Nothing)kullanır.

  • İsteğe bağlı parametre türüne Objectsahipse ve varsayılan bir değer belirtmiyorsa, derleyici bağımsız değişkenini System.Reflection.Missing.Valuekullanır.

Koşullu Yöntemler

Çağırma ifadesinin başvurduğu hedef yöntem bir arabirimin üyesi olmayan bir alt yordamsa ve yöntemin bir veya daha fazla System.Diagnostics.ConditionalAttribute özniteliği varsa, ifadenin değerlendirilmesi kaynak dosyada o noktada tanımlanan koşullu derleme sabitlerine bağlıdır. Özniteliğin her örneği, koşullu derleme sabitini adlandıran bir dize belirtir. Her koşullu derleme sabiti, bir koşullu derleme deyiminin parçasıymış gibi değerlendirilir. Sabit olarak değerlendirilirse True, ifade çalışma zamanında normal olarak değerlendirilir. Sabit olarak değerlendirilirse False, ifade hiç değerlendirilmez.

özniteliği aranırken, geçersiz kılınabilir bir yöntemin en çok türetilmiş bildirimi denetlenmiştir.

Not. Öznitelik, işlevlerde veya arabirim yöntemlerinde geçerli değildir ve her iki yöntemde de belirtilirse yoksayılır. Bu nedenle, koşullu yöntemler yalnızca çağırma deyimlerinde görünür.

Tür Bağımsız Değişkeni Çıkarımı

Tür parametrelerine sahip bir yöntem tür bağımsız değişkenleri belirtilmeden çağrıldığında, çağrının tür bağımsız değişkenlerini denemek ve çıkarabilmek için tür bağımsız değişkeni çıkarımı kullanılır. Bu, tür bağımsız değişkenleri önemsiz bir şekilde çıkarılabildiğinde tür parametreleriyle bir yöntemi çağırmak için daha doğal bir söz dizimi kullanılmasını sağlar. Örneğin, aşağıdaki yöntem bildirimi göz önünde bulundurulduğunda:

Module Util
    Function Choose(Of T)(b As Boolean, first As T, second As T) As T
        If b Then
            Return first
        Else
            Return second
        End If
    End Function
End Class

açıkça bir tür bağımsız değişkeni belirtmeden yöntemini çağırmak Choose mümkündür:

' calls Choose(Of Integer)
Dim i As Integer = Util.Choose(True, 5, 213)
' calls Choose(Of String)
Dim s As String = Util.Choose(False, "a", "b") 

Tür bağımsız değişkeni çıkarımı aracılığıyla, tür bağımsız değişkenleri Integer ve String bağımsız değişkenlerinden yöntemine belirlenir.

Tür bağımsız değişkeni çıkarımı, ifade yeniden sınıflandırması bağımsız değişken listesindeki lambda yöntemlerinde veya yöntem işaretçilerinde gerçekleştirilmeden önce gerçekleşir, çünkü bu iki tür ifadenin yeniden sınıflandırılması, parametre türünün bilinmesini gerektirebilir. Bir dizi bağımsız değişken A1,...,Anverildiğinde, bir dizi eşleşen parametre P1,...,Pn ve yöntem türü parametresi T1,...,Tnkümesi verildiğinde, bağımsız değişkenler ve yöntem türü parametreleri arasındaki bağımlılıklar ilk olarak aşağıdaki gibi toplanır:

  • Değişmez değer ise AnNothing , hiçbir bağımlılık oluşturulmaz.

  • Bir An lambda yöntemiyse ve türü Pn ise veya bir temsilci türüyse System.Linq.Expressions.Expression(Of T), burada T bir temsilci türü oluşturulur,

  • Lambda yöntemi parametresinin türü, ilgili parametrenin Pntüründen çıkarılacaksa ve parametrenin türü bir yöntem türü parametresine Tnbağlıysa An , üzerinde bir bağımlılığı Tnvardır.

  • Lambda yöntemi parametresinin türü belirtilmişse ve karşılık gelen parametrenin Pn türü bir yöntem türü parametresine Tnbağlıysa Tn , üzerinde bir bağımlılığı Anvardır.

  • dönüş türü Pn bir yöntem türü parametresine Tnbağlıysa, Tn öğesine bağımlılığı Anvardır.

  • An Bir yöntem işaretçisi ve türü Pn ise, bir temsilci türü,

  • dönüş türü Pn bir yöntem türü parametresine Tnbağlıysa, Tn öğesine bağımlılığı Anvardır.

  • Bir tür oluşturulursa ve türü Pn bir yöntem türü parametresine Tnbağımlıysa PnTn, üzerinde Anbir bağımlılığı vardır.

  • Aksi takdirde bağımlılık oluşturulmaz.

Bağımlılıklar toplandıktan sonra, bağımlılığı olmayan tüm bağımsız değişkenler ortadan kalkar. Herhangi bir yöntem türü parametresinin giden bağımlılıkları yoksa (yöntem türü parametresi bir bağımsız değişkene bağımlı değildir), tür çıkarımı başarısız olur. Aksi takdirde, kalan bağımsız değişkenler ve yöntem türü parametreleri güçlü bir şekilde bağlı bileşenler halinde gruplandırılır. Kesin olarak bağlı bir bileşen, bileşendeki herhangi bir öğeye diğer öğelere bağımlılıklar aracılığıyla ulaşılabilen bir dizi bağımsız değişken ve yöntem türü parametresidir.

Güçlü bir şekilde bağlı bileşenler topolojik olarak sıralanır ve topolojik sırayla işlenir:

  • Kesin olarak yazılan bileşen yalnızca bir öğe içeriyorsa,

    • Öğe zaten tamamlandı olarak işaretlenmişse atlayın.

    • Öğesi bir bağımsız değişkense, bağımsız değişkenden buna bağlı olan yöntem türü parametrelerine tür ipuçları ekleyin ve öğeyi tamamlandı olarak işaretleyin. Bağımsız değişken hala çıkarılma türlerine ihtiyaç duyan parametrelere sahip bir lambda yöntemiyse, Object bu parametrelerin türlerini çıkarsayın.

    • öğesi bir yöntem türü parametresiyse, yöntem türü parametresini bağımsız değişken türü ipuçları arasında baskın tür olacak şekilde çıkarsayın ve öğeyi tamamlandı olarak işaretleyin. Tür ipucunda dizi öğesi kısıtlaması varsa, yalnızca verilen türdeki diziler arasında geçerli olan dönüştürmeler (örn. kovaryant ve iç dizi dönüştürmeleri) dikkate alınır. Tür ipucunda genel bağımsız değişken kısıtlaması varsa, yalnızca kimlik dönüştürmeleri dikkate alınır. Baskın tür seçilemiyorsa çıkarım başarısız olur. Herhangi bir lambda yöntemi bağımsız değişken türü bu yöntem türü parametresine bağlıysa, tür lambda yöntemine yayılır.

  • Kesin olarak yazılan bileşen birden fazla öğe içeriyorsa, bileşen bir döngü içerir.

    • Bileşendeki bir öğe olan her yöntem türü parametresi için, yöntem türü parametresi tamamlandı olarak işaretlenmemiş bir bağımsız değişkene bağımlıysa, bu bağımlılığı çıkarım işleminin sonunda denetlenecek bir onay işaretine dönüştürün.

    • Kesin olarak belirlenmiş bileşenlerin belirlendiği noktada çıkarım işlemini yeniden başlatın.

Tüm yöntem türü parametreleri için tür çıkarımı başarılı olursa onaylara dönüştürülen tüm bağımlılıklar denetlenir. Bağımsız değişkenin türü, yöntem türü parametresinin çıkarılmış türüne örtük olarak dönüştürülebilirse onay başarılı olur. Onay başarısız olursa tür bağımsız değişken çıkarımı başarısız olur.

Bağımsız değişken için bağımsız değişken A türü Ta ve parametre için Pparametre türü Tp verildiğinde, tür ipuçları aşağıdaki gibi oluşturulur:

  • Herhangi bir yöntem türü parametresi içermiyorsa Tp hiçbir ipucu oluşturulmaz.

  • ve Ta aynı dereceye sahip dizi türleriyse Tp ve öğesini öğesi türleriyle Ta değiştirin TaTp ve Tp bu işlemi bir dizi öğesi kısıtlamasıyla yeniden başlatın.

  • Yöntem türü parametresiyse Tp , Ta varsa geçerli kısıtlamayla bir tür ipucu olarak eklenir.

  • A Lambda yöntemiyse ve Tp bir temsilci türü veya System.Linq.Expressions.Expression(Of T)ise, burada T her lambda yöntemi parametre türü ve karşılık gelen temsilci parametre türü TDTL için, ve ile TD değiştirin TaTLTp ve kısıtlama olmadan işlemi yeniden başlatın. Ardından değerini lambda yönteminin dönüş türüyle değiştirin Ta ve:

    • normal bir lambda yöntemiyse A , değerini temsilci türünün dönüş türüyle değiştirin Tp ;
    • zaman uyumsuz bir lambda yöntemiyse ve temsilci türünün dönüş türü bazı için formuna Task(Of T) sahipse A değerini şununla TdeğiştirinTp: ;T
    • yineleyici bir lambda yöntemiyse A ve temsilci türünün dönüş türü form IEnumerator(Of T) veya IEnumerable(Of T) bazıları Tiçin ise değerini bu Tile değiştirinTp.
    • Ardından, kısıtlama olmadan işlemi yeniden başlatın.
  • Yöntem işaretçisiyse A ve Tp bir temsilci türüyse, işaret edilen yöntemin için en uygun olduğunu belirlemek için Tpparametresini Tp kullanın. En uygun yöntem varsa değerini yöntemin dönüş türüyle ve Tp temsilci türünün dönüş türüyle değiştirin Ta ve işlemi kısıtlama olmadan yeniden başlatın.

  • Aksi takdirde, Tp bir tür oluşturulmalıdır. verilen TG, genel türü Tp.

    • iseTa, türünden TGdevralır veya türü TG tam olarak bir kez uygular, ardından ve Tpx öğesinden TaTpeşleşen her tür bağımsız değişkeni Tax için ve ile Tpx değiştirin TaxTaTp ve işlemi genel bağımsız değişken kısıtlamasıyla yeniden başlatın.TG

    • Aksi takdirde, genel yöntem için tür çıkarımı başarısız olur.

Tür çıkarımının başarısı, yöntemin uygulanabilir olduğunu garanti etmez.