2013-12-12 29 views
5

SystemVerilog aşağı yayınlamayı destekliyor mu (temel nesneyi türetilmiş bir nesneye dönüştürmek)? Öyleyse nasıl?SystemVerilog, downcasting'i destekliyor mu?

class base; 
    int a = 5; 
endclass 

class extend extends base; 
    int b = 1; 
endclass 

module test; 

    initial begin 
    base m_base; 
    extend m_extend; 

    m_base = new(); 
    m_extend = new(); 
    $cast(m_extend, m_base); 
    $display(m_extend.a); 
    end 
endmodule 

Değiştir ve EDA içinde oyun alanı örneğini yeniden:

aşağıdaki mahzun örnek çalışmıyor http://www.edaplayground.com/s/4/581

cevap

7

Evet, downcast yapabilirsiniz. Örneğiniz doğru sözdizimi ve aslında derleme yapıyor. Ancak, döküm başarısız olduğundan bir çalışma zamanı hatası alıyorsunuz.

Örnekte, örneğin temel nesnenin tanıtıcısı, türetilen türden bir nesneye başvuruda bulunuluyorsa, başarılı bir şekilde yayınlayabildiğinizden, örneğin, başarısız oluyor. Bir işlev olarak $cast numaralı telefonu arayabilir ve yayınlamanın başarılı olup olmadığını belirten bir boole döndürür.

class animal; 
    function void eat(); 
    endfunction 
endclass 

class dog extends animal; 
    function void bark(); 
    $display("woof"); 
    endfunction 
endclass 

class cat extends animal; 
    function void meow(); 
    $display("meow"); 
    endfunction 
endclass 

module test; 

    initial begin 
    dog a_dog = new(); 
    cat a_cat = new(); 

    animal animals[$]; 
    animals.push_back(a_dog); 
    animals.push_back(a_cat); 

    foreach (animals[i]) begin 
     dog another_dog; 
     animals[i].eat(); 
     if ($cast(another_dog, animals[i])) begin 
     $display("Found a dog!"); 
     another_dog.bark(); 
     end 
    end 

    end 
endmodule 

Çıkışlar: Burada

bir örnektir

# Found a dog! 
# woof 

Bkz http://www.edaplayground.com/s/474/586

+0

Yani mahzun eserler yalnızca: Burada

class ext_more extends extend; int c; endclass initial begin base m_base; extend m_extend; ext_more m_ext_more; m_ext_more = new(); m_base = m_ext_more; $cast(m_extend, m_base); // legal, casting a subclass object to a parent handle $display(m_extend.a); end 

bazı çalışma örneğidir Kaynak nesne ilk kez yayınlandı. –

+1

Evet, çoğu bölüm için. Açık bir yükselişin sonucu olmamalıdır, ancak türetilmiş bir nesnenin bir nesnesini işaret eden taban tipi referansa sahip olmanız gerekir. – dwikle

3

IEEE Std 1800-2012 § 8,16 "Döküm" devletler:

It Kalıtım ağacında (ifade türünün bir üst sınıfı veya atası) daha yüksek bir sınıf türü değişkenine alt sınıf türü ifadesi atamak her zaman yasaldır. Alt sınıf türlerinden birinin değişkenine bir üst sınıf türü değişkenini doğrudan atamak yasa dışı olacaktır. Ancak, alt sınıf tutamacı alt sınıf değişkeni ile uyumlu olan bir nesneye başvuruda bulunması koşuluyla, bir alt sınıf türünün değişkenine bir üst sınıf tanıtıcısı atamak için $cast kullanılabilir.

Aşağıdakiler, bir alt sınıf nesnesi, alt sınıf olarak okunamadığından artar. Hedef typetypes karşılaştırılabilir olmalıdır ile

m_base = new(); 
$cast(m_extend, m_base); // destination type != source object type 

uyumlu olmalıdır doğru kaynak sapın nesne yayınlamak için:

m_extend = new(); 
m_base = m_extend; 
$cast(m_extend, m_base); // destination type == source object type 

downcasting kalıtım seviyeleri ile çalışabilir. Aşağıdaki örnek, bir torun nesnesi işaret eden bir taban sınıfı kolu uzatmak sınıfı (torun nesnenin üst sınıfı) için demir ediliyor gösterir: http://www.edaplayground.com/s/6/587