Substituição de função e sobrecarga em C ++ e Delphi
SPACESOFT 【Areia da noite escura】
Na programação orientada a objetos, quando a subclasse continua as funções da classe base, a subclasse pode precisar lidar com algumas das funções de maneira diferente da classe base, como:
Classe Chuman
{
público:
Void Saymyname () // Imprima o nome do objeto
{
cout << oi, eu sou um humano << endl;
}
};
Então é óbvio, se sua subclasse tiver uma função Saymyname com o mesmo nome, o mesmo parâmetro e valor de retorno (uma frase, a mesma função), qual função ela chamará? Por exemplo, há uma classe CMARK agora
Classe CMARK: Public Chuman
{
público:
Void Saymyname ()
{
cout << oi, eu sou mark << endl;
}
};
Então temos que perguntar, o seguinte segmento do programa:
Chuman *ph = new cmark;
se (pH)
ph-> saymyname ();
outro
cout << Erro de elenco! << endl;
excluir pH;
pH = nulo;
Oi, eu sou Mark que queremos imprimir?
não. Ele produz oi, eu sou humano. É horrível, e quando apontamos para uma pessoa e pedimos que ele diga seu nome, ele nos diz que é "uma pessoa" em vez de dizer seu nome. A razão para esse problema é que apontando para a classe derivada do público com o ponteiro da classe base, você pode acessar as funções de membro da classe derivada que continuam da classe base. Mas se houver funções com o mesmo nome na classe derivada, o resultado ainda está acessando a função do mesmo nome da classe base, em vez da função da própria classe derivada. De fato, o que queremos é determinar qual dessas funções com o mesmo nome deve ser chamada pelo tipo real de um objeto, ou seja, essa resolução é dinâmica. Ou podemos dizer que, quando um objeto é um subtipo, sua implementação de mesmo nome na subclasse substitui a implementação da classe base.
Vamos começar com o manuseio do C ++ desse problema.
Este é um exemplo típico de polimorfismo em C ++. Para ser específico, é usar palavras -chave virtuais para descrever a função como uma função virtual.
Classe Chuman
{
público:
virtual void Saymyname () // Imprima o nome do objeto
{
cout << oi, eu sou um humano << endl;
}
};
Dessa forma, outros códigos ainda são os mesmos, mas nosso CMARK já sabe como dizer seu nome. Não importa se a função Saymyname () do CMARK adicionou uma palavra -chave virtual, porque, de acordo com as disposições da sintaxe C ++, porque substitui a função crimana do mesmo nome, ela se torna virtual. Quanto a por que uma palavra -chave virtual tem um efeito tão mágico? O C ++ FAQ Lite explica isso da seguinte forma: em C ++, "as funções de membro virtual são determinadas dinamicamente (em tempo de execução). Ou seja, as funções de membro (no tempo de execução) são selecionadas dinamicamente e a seleção é baseada no tipo do objeto. Não o tipo de ponteiro/referência a esse objeto ". Portanto, nosso PH descobre que ele realmente aponta para um objeto do tipo CMARK, não o Chuman declarado por seu próprio tipo, por isso chama inteligentemente o Saymyname da CMARK.
Delphi usa palavras -chave substituídas para ilustrar as substituições de funções. A função substituída deve ser virtual ou dinâmica, ou seja, a função deve conter um desses dois indicadores quando declarado, como:
Procedimento Draw;
Quando você precisa substituir, você só precisa redectar com o indicador de substituição na subclasse.
Procedimento Desenho;
Syntaticamente, as declarações como virtuais e dinâmicas são equivalentes. A diferença é que o primeiro otimiza a velocidade na implementação, enquanto o último otimiza o tamanho do código.
E se a classe base e a subclasse contiverem o mesmo nome e parâmetro da função, e o indicador de substituição não for adicionado à subclasse? Isso também é sintaticamente correto. Isso significa que a implementação da função da função da subclasse oculta a implementação da classe base, embora ambos existam na classe derivada. Então vamos voltar à situação mostrada no primeiro exemplo no início deste artigo: quando apontamos para uma pessoa e pedimos que ele diga seu próprio nome, ele nos diz que é "uma pessoa", em vez de dizer o seu próprio nome.
Vale a pena notar que, diferentemente da função de sobrecarga e da função de sobrecarga, que geralmente chamamos de sobrecarga em C ++, em Delphi, apenas a sobrecarga é o que geralmente chamamos de sobrecarga. Obviamente, quando a sobrecarga de queda da função é a mesma que os parâmetros de função da classe base, a implementação da classe base está oculta, assim como a mencionada acima. Substituir significa tornar a função substituída invisível e, de fato, substituir, e a implementação original desaparecerá. Por esse motivo, muitos artigos e até alguns livros traduziram por engano a substituição em sobrecarga, o que eu acho que não é apropriado.