Definição de funções

De GNU Octave
Revisão em 14h45min de 21 de janeiro de 2013 por Jgrocha (Discussão | contribs)

(dif) ← Revisão anterior | Revisão atual (dif) | Revisão seguinte → (dif)
Ir para: navegação, pesquisa

Até agora, vimos que se pode transformar uma sucessão de instruções Octave num programa. O programa pode ser potencialmente muito grande, se for utilizado para resolver um problema complicado.

No entanto, como se viu, todas as variáveis de um programa são variáveis globais. Por outro lado, o próprio programa, se crescer muito, começa a ficar complicado encontrar e corrigir algum erro de programação. Por último, não é viável estarem mais do que um programador a trabalhar no mesmo programa.

Por ultrapassar estas limitações das scripts, o Octave tem a possibilidade de se definirem funções. As funções resolvem os problemas enunciados. Por um lado, as variáveis dentro das funções são locais e não interferem com outras variáveis globais. Por outro lado, permitem dividir a lógica de um grande problema em pequenas funções que se compõem para obter o resultado final. Por último, permitem que vários programadores possam estar a trabalhar e testar as diferentes funções necessárias para resolver um problema complicado.

Para além destas razões, as funções permitem mais flexibilidade na gestão das variáveis, permitindo, além das variáveis de âmbito local, ter variáveis globais ou persistentes.

Sintaxe

Para definir uma função é preciso criar um ficheiro .m com o nome da função, tal como se faz para criar um programa. Ou seja, se se pretende criar uma função quadrado, tem que se criar um novo documento quadrado.m, onde será definida a função.

A definição de uma função difere de um programa porque começa com a palavra function. Basta começar por esta palavra, e ficamos logo a saber que se trata de uma função e não de um programa.

O início da definição de uma função é sempre da forma:

function [resultados] = nome_da_função(argumentos)
  • Os resultados são uma lista de variáveis separadas por vírgulas. São os valores que serão retornados quando se invoca a função;
  • O nome_da_função tem que ser igual ao nome do documento, e será usado para invocar a função;
  • Os argumentos são uma lista de variáveis separadas por vírgulas, que vão receber os valores passados à função quando esta é invocada.

A estrutura genérica utiliza para definir uma função é a seguinte:

function [resultados] = nome_da_função(argumentos)
    corpo
endfunction
Uma função muito simples

Vamos começar com um exemplo muito simples. Considere a função seguinte:

function res = quadrado(x)res = x*x;
endfunction

Esta função tem:

  • Uma só variável de resultado, que se designa res;
  • O nome da função é quadrado, pelo que esta função tem que estar guardada num documento quadrado.m;
  • Só existe um argumento (de entrada), que é a variável x. Ou seja, x vai receber o valor passado à função.

Para invocar esta função, usa-se o nome da mesma, como a seguir se exemplifica.

>>> quadrado(3)
ans =  9
>>> area = quadrado(14)
area =  196
>>>

Relembra-se que tem que estar na pasta onde está guardada a função. Ou seja, o Octave tem que saber onde encontrar o documento quadrado.m.

>>> dir quadrado.m
quadrado.m
>>>

Se o comando anterior resultar em:

>>> dir quadrado.m
warning: dir: nonexistent file `quadrado.m'
>>>

significa que o Octave não está na mesma pasta onde foi guardado o documento quadrado.m e, por isso, não vai conseguir invocar a função quadrado.

Uma função documentada

Depois de escrever o cabeçalho de uma função, deve-se sempre escrever uma sequência de comentários (até aparecer o código da função ou uma linha em branco) que serão utilizados para prestar ajuda sobre a função.

Considere a função seguinte, onde se acrescentaram comentários (linhas começadas por %) logo a seguir ao cabeçalho.

function s = senoemgraus(graus)
% senoemgraus(graus) 
%	Calcula o seno, dado um valor em graus, e não em radianos.
% 	O cálculo é efetuado convertendo o valor dado em radianos com a expressão:
%		radianos = graus*pi/180
s = sin(graus*pi/180);
endfunction

Se invocar a função, aparece o resultado esperado. Se invocar a ajuda sobre a função, aparece-lhe os comentários que foram colocados na função.

>>> senoemgraus(90)
ans =  1
>>> help senoemgraus
`senoemgraus' is a function from the file /home/jgr/Documentos/Aulas/12131S/OCV
/octave/senoemgraus.m
 
 senoemgraus(graus) 
	Calcula o seno, dado um valor em graus, e não em radianos.
 	O cálculo é efetuado convertendo o valor dado em radianos com a expressão:
		radianos = graus*pi/180
 
Additional help for built-in functions and operators is
available in the on-line version of the manual.  Use the command
`doc <topic>' to search the manual index.
 
Help and information about Octave is also available on the WWW
at http://www.octave.org and via the help@octave.org
mailing list.
>>>

Além dos comentários, também é indicado o documento exato onde a função está definida.

Uma função com validações

Há funções que só estão definidas para um determinado domínio, e não podem ser invocadas para todos os valores, por exemplo.

Para limitar a execução de uma função a determinadas condições, podem-se acrescentar validações logo no início, de forma a reportar um erro caso as condições não se verifiquem.

No exemplo seguinte, se o número de argumentos não for exatamente 2, a invocação da função é abruptamente terminada com uma mensagem de erro.

A função também termina imediatamente de igual forma se os argumentos não forem números. Ou seja, a função não aceita vetores como argumentos, por exemplo.

function area = rectarea(largura, comprimento)
% rectarea(largura, comprimento)
%	Calcula a área de um rectângulo, dada a largura e comprimento.
if (nargin != 2)
         print_usage();
endif
if !(isscalar(largura) & isscalar(comprimento))
	error ("largura e comprimento têm que ser números");
endif
area = largura * comprimento;
endfunction