Kovaryant dönüş türü nedir?


105

Java'da kovaryant dönüş türü nedir? Genel olarak nesne yönelimli programlamada?


5
bu blog yazısı ( blogs.oracle.com/sundararajan/entry/… ), burada bilgi tabanına ekleyerek açıklıyor.
Akhil Jain

@AkhilJain: Bu blog yazısı harika ve basit. Java'nın kovaryant dönüş türlerini nasıl desteklediğine dair şimdiye kadar gördüğüm en iyi örnek açıklaması.
kevinarpe

@kevinarpe teşekkürler, bu kadar çok insana yardımcı olmasından memnunum.
Akhil Jain

Yanıtlar:


143

Kovaryant dönüş, bir yöntemi geçersiz kıldığında, geçersiz kılma yönteminin dönüş türünün, geçersiz kılınan yöntemin dönüş türünün bir alt türü olmasına izin verildiği anlamına gelir.

Bunu bir örnekle açıklığa kavuşturmak için, Object.clone()bir tür döndürmek üzere bildirilen ortak bir durum - Object. Bunu kendi sınıfınızda aşağıdaki gibi geçersiz kılabilirsiniz:

public class MyFoo
{

   ...

   // Note covariant return here, method does not just return Object
   public MyFoo clone()
   {
       // Implementation
   }
}

Buradaki fayda, bir MyFoo nesnesine açık bir referans tutan herhangi bir yöntemin clone(), dönüş değerinin bir örneği olduğunu (çevrim yapmadan) çağırıp bilebilir olmasıdır MyFoo. Kovaryant dönüş türleri olmadan, MyFoo'daki geçersiz kılınan yöntemin geri dönmesi için bildirilmesi gerekir Object- ve bu nedenle çağıran kodun, yöntem çağrısının sonucunu açıkça aşağıya indirmesi gerekir (her iki tarafın da "bildiği" düşünülse bile, yalnızca bir MyFoo örneği olabilir. ).

Özel bir şey olmadığına clone()ve geçersiz kılınan herhangi bir yöntemin ortak değişken bir dönüşe sahip olabileceğine dikkat edin - burada bir örnek olarak kullandım çünkü bunun genellikle yararlı olduğu standart bir yöntem.


onunla ilgili olması gerekiyordu değil mi List<Foo>ve List<FooBar>?
2016

2
Bu, burada sorulan kovaryant dönüş türü yerine daha geniş anlamda kovaryant türleri . Yine de aynı temel ilke - üst düzey tanımını clone()a olarak düşünebilir Method<Void, Object>ve daha spesifik Method<Void, MyFoo>olanın bu ebeveyn türüne atanabilir olup olmadığını sorabilirsiniz . Hangisi, ancak ve ancak Java yöntemleri, dönüş türlerinde eşdeğişken ise.
Andrzej Doyle

38

İşte başka bir basit örnek:

Animal sınıf

public class Animal {

    protected Food seekFood() {

        return new Food();
    }
}

Dog sınıf

public class Dog extends Animal {

    @Override
    protected Food seekFood() {

        return new DogFood();
    }
}

Bu dönüş türünü değiştirmek mümkündür Dogs' seekFood()yöntemin DogFoodbir alt - Food: aşağıda gösterildiği gibi,

@Override
protected DogFood seekFood() {

    return new DogFood();
}

Gayet yasal bir ağır basan, ve dönüş tipi Dogbireyin seekFood()yöntemi olarak bilinir eşdeğişkin dönüş türü .


8

JDK 1.5 sürümünden itibaren, Java'da kovaryant türleri tanıtıldı. ve size basit bir durumla açıklayacağım: Bir işlevi geçersiz kıldığımızda, işlevin davranışında değişiklik yapmasına izin verilir , bu kitapların çoğunda okuyacağınız şeydir, ancak {yazarların} gözden kaçırdıkları dönüş türünü de değiştirebileceğimizdir. açıklama için aşağıdaki bağlantıyı kontrol edin, yöntemin Temel sürümünün dönüş türüne atanabildiği sürece dönüş türünü değiştirebiliriz.

Dolayısıyla, türetilmiş türleri döndürmenin bu özelliğine KOVARYANT denir ...

Geçersiz kılınan yöntemler dönüş türünde farklılık gösterebilir mi?


7

kovaryant Dönüş türleri basitçe kendi Sınıf referansını veya alt sınıf referansını döndürmek anlamına gelir.

class Parent {
 //it contain data member and data method
}

class Child extends Parent { 
//it contain data member and data method
 //covariant return
  public Parent methodName() {
     return new Parent();
          or 
     return Child();
  }

}

1
Ayrıca durumu da içerir Parent.foo()döner bir ilgisiz türü Ave Child.foo()döner bir tür Btüretilen A.
Davis Herring

2

Yukarıdaki cevaplara eklemek için, geçersiz kılma yönteminin (alt sınıf yöntemi) dönüş türünün, geçersiz kılınan yöntemin (üst sınıf yöntemi) dönüş türünün bir alt sınıfı olması kısıtlamasıyla, eş değişken dönüş türleri arasında geçersiz kılma mümkündür. Bu, Java 5'ten itibaren geçerlidir.


1

Kovaryant dönüş türü, dönüş türünün alt sınıfla aynı yönde değişebileceğini belirtir

class One{  
    One get(){return this;}  
}  

class Two extends One{  
  Two get(){return this;}  

void message(){
  System.out.println("After Java5 welcome to covariant return type");
}  

public static void main(String args[]){  
    new Two().get().message();  
}  
}

Java 5'ten önce, dönüş türünü değiştirerek herhangi bir yöntemi geçersiz kılmak mümkün değildi. Ama şimdi, Java5'ten beri,

Alt sınıf, dönüş türü İlkel Olmayan olan ancak dönüş türünü alt sınıf türü olarak değiştiren herhangi bir yöntemi geçersiz kılarsa, dönüş türünü değiştirerek yöntemi geçersiz kılmak mümkündür.


1
  • Sınıf hiyerarşisinde bulunan kafa karıştırıcı tür yayınlarından kaçınmaya yardımcı olur ve böylece kodu okunabilir, kullanılabilir ve sürdürülebilir hale getirir.

  • Yöntemleri geçersiz kılarken daha spesifik dönüş türlerine sahip olma özgürlüğüne sahibiz .

  • İadelerde çalışma zamanı ClassCastExceptions'ı önlemede yardım

referans: www.geeksforgeeks.org


0
  • Java'daki kovaryant dönüş türü, geçersiz kılınan yöntemin dönüş türünü daraltmaya izin verir.
  • Bu özellik, istemci tarafında alt yayınlardan kaçınmaya yardımcı olacaktır. Programcının tip kontrol ve aşağı döküm ihtiyacı olmadan programlamasına izin verir.
  • Kovaryant dönüş türü her zaman yalnızca ilkel olmayan dönüş türleri için çalışır.
interface Interviewer {
    default Object submitInterviewStatus() {
        System.out.println("Interviewer:Accept");
        return "Interviewer:Accept";
    }
}
class Manager implements Interviewer {
    @Override
    public String submitInterviewStatus() {
        System.out.println("Manager:Accept");
        return "Manager:Accept";
    }
}
class Project {
    public static void main(String args[]) {
        Interviewer interviewer = new Manager();
        interviewer.submitInterviewStatus();
        Manager mgr = new Manager();
        mgr.submitInterviewStatus();
    }
}

Diğer örnek Java'dan,

UnaryOperator.java

@FunctionalInterface
public interface UnaryOperator<T> extends Function<T, T> {

    /**
     * Returns a unary operator that always returns its input argument.
     *
     * @param <T> the type of the input and output of the operator
     * @return a unary operator that always returns its input argument
     */
    static <T> UnaryOperator<T> identity() {
        return t -> t;
    }
}

Function.java

@FunctionalInterface
public interface Function<T, R> {

    ........
    ........
    ........
    ........

    static <T> Function<T, T> identity() {
        return t -> t;
    }
}

0

Java5'ten önce, dönüş türünü değiştirerek herhangi bir yöntemi geçersiz kılmak mümkün değildi. Ama şimdi, Java5'ten beri, eğer alt sınıf, dönüş türü İlkel Olmayan bir yöntemi geçersiz kılarsa, ancak dönüş türünü alt sınıf türü olarak değiştirirse, dönüş türünü değiştirerek yöntemi geçersiz kılmak mümkündür.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.