Assinatura de tipo - Type signature

Em ciência da computação , uma assinatura de tipo ou anotação de tipo define as entradas e saídas para uma função, sub-rotina ou método . Uma assinatura de tipo inclui o número, tipos e ordem dos argumentos contidos por uma função. Uma assinatura de tipo é normalmente usada durante a resolução de sobrecarga para escolher a definição correta de uma função a ser chamada entre muitos formulários sobrecarregados.

Exemplos

C / C ++

Em C e C ++ , a assinatura de tipo é declarada pelo que é comumente conhecido como protótipo de função . Em C / C ++, uma declaração de função reflete seu uso ; por exemplo, um ponteiro de função com a assinatura seria chamado como: (int)(char, double)

char c;
double d;
int retVal = (*fPtr)(c, d);

Erlang

Em Erlang , as assinaturas de tipo podem ser declaradas opcionalmente, como:

-spec(function_name(type1(), type2(), ...) -> out_type()).

Por exemplo:

-spec(is_even(number()) -> boolean()).}}

Haskell

Uma assinatura de tipo em Haskell geralmente assume a seguinte forma:

functionName :: arg1Type -> arg2Type -> ... -> argNType

Observe que o tipo de resultado pode ser considerado como tudo após o primeiro argumento fornecido. Isso é uma consequência do currying , que é possível devido ao suporte de Haskell para funções de primeira classe ; esta função requer duas entradas onde um argumento é fornecido e a função é "curried" para produzir uma função para o argumento não fornecido. Assim , chamar , where , produz uma nova função que pode ser chamada para produzir . f xf :: a -> b -> cf2 :: b -> cf2 bc

As especificações de tipo real podem consistir em um tipo real, como Integer, ou uma variável de tipo geral que é usada em funções polimórficas paramétricas , como , ou , ou . Então, podemos escrever algo como: abanyTypefunctionName :: a -> a -> ... -> a

Uma vez que Haskell suporta funções de ordem superior , as funções podem ser passadas como argumentos. Isso é escrito como: functionName :: (a -> a) -> a

Esta função recebe uma função com assinatura de tipo e retorna dados de saída do tipo . a -> aa

Java

Na máquina virtual Java , assinaturas de tipo interno são usadas para identificar métodos e classes no nível do código da máquina virtual.

Exemplo: o método é representado em bytecode como . String String.substring(int, int)Ljava/lang/String.substring(II)Ljava/lang/String;

A assinatura do mainmétodo se parece com isto:

public static void main(String[] args);

E no bytecode desmontado, ele assume a forma de Lsome/package/Main/main:([Ljava/lang/String;)V

A assinatura do main()método para o método contém três modificadores:

  • publicindica que o método pode ser chamado por qualquer objeto.main()
  • staticindica que o método é um método de classe.main()
  • voidindica que o método não tem valor de retorno.main()

Assinatura

Uma assinatura de função consiste no protótipo da função. Ele especifica as informações gerais sobre uma função, como nome, escopo e parâmetros. Muitas linguagens de programação usam nomes mutilados para passar mais informações semânticas dos compiladores para os linkers. Além de mutilar, há um excesso de informações em uma assinatura de função (armazenada internamente para a maioria dos compiladores) que não está prontamente disponível, mas pode ser acessada.

Compreender a noção de uma assinatura de função é um conceito importante para todos os estudos de ciência da computação.

  • As técnicas modernas de orientação a objetos usam interfaces , que são essencialmente modelos feitos de assinaturas de funções.
  • C ++ usa sobrecarga de função com várias assinaturas.

A prática de herança múltipla requer a consideração das assinaturas de função para evitar resultados imprevisíveis.

A teoria da ciência da computação, e o conceito de polimorfismo em particular, fazem muito uso do conceito de assinatura de função.

Na linguagem de programação C, a assinatura é aproximadamente equivalente à sua definição de protótipo .

O termo "assinatura" pode ter outros significados em ciência da computação:

  • As assinaturas de arquivo podem identificar ou verificar o conteúdo de um arquivo.
  • As assinaturas do banco de dados podem identificar ou verificar o esquema ou uma versão de um banco de dados.
  • Na família de linguagens de programação ML , "assinatura" é usada como uma palavra-chave que se refere a uma construção do sistema de módulo que desempenha o papel de uma interface .

Assinatura do método

Na programação de computadores , especialmente na programação orientada a objetos , um método é comumente identificado por sua assinatura de método única , que geralmente inclui o nome do método e o número, tipos e ordem de seus parâmetros . Uma assinatura de método é o menor tipo de método.

Exemplos

C / C ++

Em C / C ++, a assinatura do método é o nome do método e o número e tipo de seus parâmetros, mas é possível ter um último parâmetro que consiste em uma matriz de valores:

int printf(const char*, ... );

A manipulação desses parâmetros pode ser feita usando as rotinas no cabeçalho da biblioteca padrão . <stdarg.h>

C #

Semelhante à sintaxe de C, as assinaturas de método em C # são compostas por um nome e o número e tipo de seus parâmetros, onde o último parâmetro pode ser uma matriz de valores:

void Add(out int sum, params int[] value);
[...]
Add(out sum, 3, 5, 7, 11, -1);  // sum == 25

Java

Em Java , uma assinatura de método é composta por um nome e o número, tipo e ordem de seus parâmetros. Os tipos de retorno e as exceções lançadas não são considerados parte da assinatura do método, nem os nomes dos parâmetros; eles são ignorados pelo compilador para verificar a exclusividade do método.

As assinaturas de método ajudam a distinguir métodos sobrecarregados (métodos com o mesmo nome) em uma classe. Os tipos de retorno não são incluídos na sobrecarga. Apenas assinaturas de método devem ser usadas para distinguir métodos sobrecarregados.

Por exemplo, os dois métodos a seguir têm assinaturas diferentes:

void doSomething(String[] x); // doSomething(String[])
void doSomething(String x);   // doSomething(String)

Todos os dois métodos a seguir têm as mesmas assinaturas:

int doSomething(int x);                   // doSomething(int)
void doSomething(int y) throws Exception; // doSomething(int)

Julia

Em Julia , as assinaturas de função assumem a seguinte forma:

commission(sale::Int, rate::Float64)::Float64

Os tipos nos argumentos são usados ​​para o envio múltiplo . O tipo de retorno é validado quando a função retorna um valor e uma exceção de tempo de execução é levantada se o tipo do valor não estiver de acordo com o tipo especificado.

Tipos abstratos são permitidos e encorajados para implementar o comportamento geral que é comum a todos os subtipos. A função acima pode, portanto, ser reescrita da seguinte maneira. Nesse caso, a função pode aceitar quaisquer subtipos Inteiro e Real de acordo.

commission(sale::Integer, rate::Real)::Real

Os tipos são totalmente opcionais em argumentos de função. Quando não especificado, é equivalente a usar o tipo Any, que é o supertipo de todos os tipos. É idiomático especificar os tipos de argumento, mas não o tipo de retorno.

Objective-C

Na linguagem de programação Objective-C , as assinaturas de método para um objeto são declaradas no arquivo de cabeçalho da interface. Por exemplo,

- (id)initWithInt:(int)value;

define um método que retorna um objeto geral (an ) e recebe um argumento inteiro. Objective-C requer apenas que um tipo em uma assinatura seja explícito, quando o tipo não é ; esta assinatura é equivalente: initWithIntidid

- initWithInt:(int)value;

Ferrugem

No Rust , as assinaturas de função assumem a seguinte forma:

fn commission(sale: u32, rate: f64) -> f64;

Referências