Notei que, com os parâmetros opcionais em C # 4, se você especificar um parâmetro opcional em uma interface , não precisará torná-lo opcional em qualquer classe de implementação:
public interface MyInterface
{
void TestMethod(bool flag = false);
}
public class MyClass : MyInterface
{
public void TestMethod(bool flag)
{
Console.WriteLine(flag);
}
}
e portanto:
var obj = new MyClass();
obj.TestMethod(); // compiler error
var obj2 = new MyClass() as MyInterface;
obj2.TestMethod(); // prints false
Alguém sabe por que os parâmetros opcionais são projetados para funcionar dessa maneira?
Por um lado, suponho que a capacidade de substituir qualquer valor padrão especificado nas interfaces seja útil, mas para ser sincero, não tenho certeza se você deve especificar valores padrão na interface, pois isso deve ser uma decisão de implementação.
Por outro lado, essa desconexão significa que você nem sempre pode usar a classe concreta e a interface de forma intercambiável. É claro que isso não seria um problema se o valor padrão for especificado na implementação, mas se você estiver expondo sua classe concreta como interface (usando alguma estrutura do IOC para injetar a classe concreta, por exemplo), então realmente não há ponto que possui o valor padrão, pois o chamador sempre deve fornecê-lo de qualquer maneira.
MyInterface
e chamá-lo com o parâmetro opcional:((MyInterface)obj).TestMethod();
.Respostas:
ATUALIZAÇÃO: Esta questão foi o assunto do meu blog em 12 de maio de 2011. Obrigado pela ótima pergunta!
Suponha que você tenha uma interface descrita e uma centena de classes que a implementam. Então você decide tornar opcional um dos parâmetros de um dos métodos da interface. Você está sugerindo que a coisa certa a fazer é que o compilador force o desenvolvedor a encontrar todas as implementações desse método de interface e torne o parâmetro opcional também?
Suponha que fizemos isso. Agora, suponha que o desenvolvedor não tenha o código fonte para a implementação:
Como o autor de D deve fazer esse trabalho? Eles são obrigados em seu mundo a ligar para o autor de B no telefone e pedir que eles enviem uma nova versão de B que faça com que o método tenha um parâmetro opcional?
Isso não vai voar. E se duas pessoas telefonarem para o autor de B e uma delas quiser que o padrão seja verdadeiro e uma delas queira que seja falso? E se o autor de B simplesmente se recusar a brincar?
Talvez nesse caso eles devessem dizer:
O recurso proposto parece acrescentar muitos inconvenientes ao programador sem aumento correspondente no poder representativo. Qual é o benefício atraente desse recurso que justifica o aumento do custo para o usuário?
ATUALIZAÇÃO: nos comentários abaixo, o supercat sugere um recurso de idioma que realmente acrescentaria energia ao idioma e permitiria alguns cenários semelhantes ao descrito nesta pergunta. Para sua informação, esse recurso - implementações padrão de métodos em interfaces - será adicionado ao C # 8.
fonte
Um parâmetro opcional é apenas marcado com um atributo. Este atributo diz ao compilador para inserir o valor padrão para esse parâmetro no site de chamada.
A chamada
obj2.TestMethod();
é substituída porobj2.TestMethod(false);
quando o código C # é compilado para IL e não no momento do JIT.De certa forma, é sempre o chamador que fornece o valor padrão com parâmetros opcionais. Isso também tem consequências no controle de versão binário: se você alterar o valor padrão, mas não recompilar o código de chamada, ele continuará usando o valor padrão antigo.
Você já não pode fazer isso se o método da interface foi implementado explicitamente .
fonte
Como os parâmetros padrão são resolvidos no tempo de compilação, não no tempo de execução. Portanto, os valores padrão não pertencem ao objeto que está sendo chamado, mas ao tipo de referência pelo qual ele está sendo chamado.
fonte
Parâmetros opcionais são como uma substituição de macro pelo que entendi. Eles não são realmente opcionais do ponto de vista do método. Um artefato disso é o comportamento que você vê onde obtém resultados diferentes se converter para uma interface.
fonte