Pergunta

Alguém pode explicar porque é que há a necessidade de adicionar um out ou no parâmetro para indicar que um tipo genérico é Co ou variante Contra em C # 4.0?

Eu tenho tentado entender por que isso é importante e por que o compilador não pode simplesmente descobrir isso ..

Obrigado,

Josh

Foi útil?

Solução

Eric Lippert, que trabalha no langauge, tem uma série de posts sobre MSDN que deve ajudar a esclarecer as questões envolvidas:
http://blogs.msdn.com/ericlippert/ arquivo / tags / Covariance + e + Contravariance / default.aspx

Ao ler os artigos mostrados nesse link, começar de baixo e trabalhar para cima.

Eventualmente, você vai chegar a # 7 (Por que precisamos de uma sintaxe em tudo?) .

Outras dicas

Nós realmente não necessidade -los, mais então precisamos abstract em classes ou ambos out e ref. Eles existem apenas para que nós, como programadores, pode fazer o nosso cristal intenção clara, de modo que programador de manutenção sabemos o que estamos fazendo, e o compilador pode verificar que estamos fazendo certo.

Bem, o principal problema é que se você tem uma hierarquia de classes como:

   class Foo { .. } 

   class Bar : Foo { .. } 

E você tem um IEnumerator<Bar>, você não pode usar isso como uma IEnumerator<Foo> mesmo que isso seria perfeitamente seguro. Em 3,5 essa força um grande número de giros dolorosas. Esta operação seria sempre seguro, mas é negado pelo sistema tipo porque ele não sabe sobre o uso covariant do parâmetro de tipo genérico. IEnumerator<Bar> só pode retornar um Bar e cada Bar é um Foo.

Da mesma forma, se você tivesse um IEqualityComparer<Foo> ele pode ser usado para comparar qualquer par de objetos do tipo Foo mesmo se um ou ambos é um Bar, mas não pode ser convertido em um IEqualityComparer<Bar> porque ele não sabe sobre o uso contravariant do parâmetro de tipo genérico. IEqualityComparer<Foo> consome apenas objetos do tipo Foo e cada Bar é um Foo.

Sem estas palavras-chave que é forçado a assumir o argumento genérico pode ocorrer tanto como um argumento para um método e como o tipo de resultado de um método, e por isso não podemos permitir com segurança uma das conversões acima.

Com eles, o tipo de sistema é livre para nos permitir com segurança upcast e abatido entre essas interfaces na direção indicada pela palavra-chave e nós obter erros indicando quando violaria a disciplina necessária para garantir que a segurança.

As palavras-chave in e out ter sido palavras-chave desde C # 1.0, e têm sido utilizados no contexto de parâmetros in- e out- a métodos.

Covariância e contravariance são restrições sobre como se pode implementar uma interface. Não há nenhuma boa maneira de inferir-los -. A única maneira, eu acho, é de uso, e que seria confuso e no final ele não iria funcionar

Jon e Joel ambos forneceu uma resposta muito completa para isso, mas a linha de fundo é que eles não são tanto necessário pelo compilador mas sim garantia ajuda a segurança da aplicação, indicando explicitamente a variação do parâmetro. Isto segue um padrão muito semelhante ao que exige a palavra-chave out ou ref tanto no sítio de vocalização eo local declaração.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top