2012-12-06 16 views
6

:Arama, const olmayan aynı sürüm aşırı yüklenmiş üye işlevinden olduğunda const niteleyiciyi kaldırmak tamam mı? Örneğin

struct B{}; 

struct A { 

const B& findB() const { /* some non trivial code */ } 

// B& findB() { /* the same non trivial code */ } 

B& findB() { 
     const A& a = *this; 
     const B& b = a.findB(); 
     return const_cast<B&>(b); 
    } 
}; 

şey sabit FINDB ve sabit olmayan FINDB elemanı işlevi içinde aynı mantık tekrarlamaktan kaçınmak istiyor olup.

return const_cast<B&>(static_cast<const A*>(this)->findB()); 

const söz konusu nesne özgün beyan edilmedi yalnızca güvenlidir uzakta Casting:

+0

Size çok referanslar gibi görünüyor. –

+0

Gerekirse işaretçiler veya kopyalar kullanmayla ilgili bir nokta yok – dchhetri

cevap

7

Evet, const sürümünü çağırmak, const nesneyi döküm, sonra const olmayan sonucu döküm const. const üye olmayan bir işleve sahip olduğunuzdan, durumun böyle olduğunu biliyor olabilirsiniz, ancak uygulamaya bağlıdır. Aşağıdakileri dikkate alınız:

class A { 
public: 

    A(int value) : value(value) {} 

    // Safe: const int -> const int& 
    const int& get() const { 
     return value; 
    } 

    // Clearly unsafe: const int -> int& 
    int& get() { 
     return const_cast<int&>(static_cast<const A*>(this)->get()); 
    } 

private: 
    const int value; 
}; 

Genel olarak, üye işlevlerim kısadır, bu nedenle tekrarlama kabul edilebilirdir. Uygulamayı bazen özel bir şablon üyesi işlevine dahil edebilir ve bunu her iki sürümden de arayabilirsiniz.

+2

"Bir const olmayan yöntemde olduğunuzdan, durumun böyle olduğunu biliyorsunuz." ne demek istiyorsun? Bir “const” yöntemi, bir 'const 'nesnesini çok iyi gönderebilir. Özel bir yardımcı işleviniz varsa –

+2

ve bir const üye işlevi değilse, sabitliği kaldırmadan const-version'dan nasıl çağırabilirim? Sabit olmayan özel üye işlevini sürekli genel üye işlevinden nasıl çağırabilirim? Hala onun sabitliği hakkında şikayet olmaz mıydı? – dchhetri

1

Burada döküm ok kullanarak o, düşünüyorum, ama kesinlikle bunu önlemek istiyorsanız, bazı şablon sihirli kullanabilirsiniz:

struct B 
{ 
    B(const B&) 
    { 
     std::cout << "oops I copied"; 
    } 
    B(){} 
}; 

struct A { 
public: 
    A(){} 
    A(const A&){ std::cout << "a is copied:(\n";} 
    const B& findB() const { return getter(*this); }  
    B& findB() { return getter(*this); } 

private: 
    template <typename T, typename V> 
    struct same_const 
    { 
     typedef V& type; 
    }; 

    template <typename T, typename V> 
    struct same_const<const T, V> 
    { 
     typedef const V& type; 
    }; 

    template <typename T> 
    static typename same_const<T,B>::type getter(T& t) { return t.b;} 

    B b; 

}; 

int main() 
{ 
    A a; 
    const A a_const; 
    const B& b1 = a.findB(); 
    B& b2 = a.findB(); 

    const B& b3 = a_const.findB(); 
    //B& b4 = a_const.findB(); 
} 
+0

woah serin hile, ama bu overkill ve benim düşünceme göre daha da kötü şeyler yapar. – dchhetri

+0

@ user814628, Katılıyorum, sadece çalışmasını istedim. – Lol4t0

İlgili konular