MDN’s new design is in Beta! A sneak peek: https://blog.mozilla.org/opendesign/mdns-new-design-beta/

Esta tradução está incompleta. Por favor, ajude a traduzir este artigo.

De modo geral, função é um "subprograma" que pode ser chamado por código externo (ou interno no caso de recursão) à função. Assim como um programa, uma função é composta por uma sequência de instruções chamada corpo da função. Valores podem ser passados para uma função e ela pode retornar um valor.

Em JavaScript, funções são objetos de primeira classe, isto é, elas podem ter propriedades e métodos como qualquer outro objeto. O que difere estes objetos de outros é que eles podem ser chamados. Funções são objetos Function.

Para mais exemplos e explicações, veja também o Guia de JavaScript sobre funções.

Descrição

Toda função em JavaScript é um objeto Function. Veja Function para informação das propriedades e métodos dos objetos Function.

Funções não são como procedimentos (procedure). Uma função sempre retorna um valor, mas um procedimento pode ou não retornar um valor.

Para retornar um valor diferente do padrão, uma função deve ter uma instrução return que específica o valor a ser retornado. Uma função sem um return retornará um valor padrão. No caso de um método construtor chamado com a palavra reservada new, o valor padrão é o valor do parâmetro this. Para todas as outras funções, o valor padrão de retorno é undefined.

Os parâmetros de uma função são chamados de argumentos da função. Argumentos são passados para a função por valor. Se uma função muda o valor de um argumento, esta mudança não é refletida globalmente ou na chamda da função. Contudo, referência de objetos são valores também, e eles são especiais: se a função muda as propriedades do objeto referenciado, estas mudanças são visíveis fora da função, como é mostrado no exemplo a seguir:

/* Declare a função 'minhaFunção' */
function minhaFuncao(objeto) {
   objeto.marca = "Toyota";
 }
 
 /*
  * Declare a variável 'meucarro';
  * crie e inicialize um novo Objeto;
  * atribua referência para 'meucarro'
  */
 var meucarro = {
   marca: "Honda",
   modelo: "Accord",
   ano: 1998
 };

 /* Exibe 'Honda' */
 console.log(meucarro.marca);

 /* Passe a referência do objeto para a função */
 minhaFuncao(meucarro);

 /*
  * Exibe 'Toyota' como valor para a propriedade 'marca'
  * do objeto, mudado pela função.
  */
 console.log(meucarro.marca);

A palavra reservada this não se refere a função sendo executada no momento, então você deve referenciar um objeto Function pelo nome, mesmo dentro do corpo da função.

Definindo funções

Há várias maneiras de definir funções:

Declaração de função (Instrução function)

Há um sintaxe especial para declarar funções (veja Instrução function para detalhes):

function nome([param[, param[, ... param]]]) {
   instruções
}
nome
O nome da função.
param
O nome de um argumento a ser passado para a função. Uma função pode ter até 255 argumentos.
instruções
As instruções que formam o corpo da função.

A expressão function (Operador function)

Uma expressão function é parecida com uma declaração function e tem até a mesma sintaxe (veja Operador function para detelhes):

function [nome]([param] [, param] [..., param]) {
   instruções
}
nome
O nome da função. Pode ser omitido, e neste caso a função é conhecida como função anônima.
param
O nome de um argumento a ser passado para a função. Uma função pode ter até 255 argumentos.
instruções
As instruções que formam o corpo da função.

O gerador de declaração de função (instrução function*)

Nota: Expressão Arrow function é uma tecnologia experimental, parte da proposta do ECMAScript 6, e ainda não é amplamente suportada pelos navegadores.

Uma expressão arrow function tem uma sintaxe curta e conecta seu valor lexicamente (veja arrow functions para mais detalhes):

([param] [, param]) => {
   instruções
}

param => expressão
param
O nome de um argumento. Quando não há argumentos deve ser indicado com o uso dos parenteses ( ). Para apenas um argumento os parenteses não são obrigatórios. (por exemplo foo => 1)
instruções ou expressão
Múltiplas instruções precisam ser envolvidas por chaves. Uma única expressão não requer chaves. A expressão também é implicitamente o valor de retorno  dessa função.

O construtor Function

Nota: O uso do construtor Function para criar funções não é recomendado uma vez que é requerido o corpo da função como string, o que pode impedir algumas otimizações por parte do motor JS e pode também causar outros problemas.

Como todos os outros objetos, objetos Function podem ser criados usando o operador new:

new Function (arg1, arg2, ... argN, corpoDaFuncao)
arg1, arg2, ... argN
Nenhum ou mais nomes para serem usados pela função como nomes formais de argumentos. Cada um deve ser uma string em conformidade com as regras para um identificador JavaScript válido ou uma lista com tais strings separadas por vírgula; por exemplo "x", "oValor", ou "a, b".
corpoDaFuncao
Uma string contento as instruções JavaScript correspondendo a definição da função.

Invocar o construtor Function como uma função (sem usar o operador new) the o mesmo efeito de invocá-lo como um construtor comum.

Parâmetros de Função

Nota: Parâmetros Default e Rest são tecnologias experimentais, parte da proposta do ECMAScript 6, e ainda não são amplamente suportados pelos navegadores.

Parâmetros Default

Parâmetro Default de função permite que parâmetros formais sejam inicializados com valores padrão se nenhum valor ou valor undefined é passado. Para mais detalhes, veja parâmetros default.

Parâmetros Rest

A sintaxe do parâmetro rest permite representar um número indefinido de argumentos em forma de array. Para mais detalhes, veja parâmetros rest.

O objeto arguments

Você pode referenciar aos argumentos da função dentro da função utilizando  o objeto arguments. Veja arguments.

  • arguments: Um objeto array-like contendo os argumentos passados para a função atualmente  em execução.
  • arguments.callee : A função atualmente em execução.
  • arguments.caller : A função que invocou a função atualmente em execução.
  • arguments.length: O número de argumentos passados para a função.

Definindo Métodos de Funções

Funções Getter e setter

Você pode definir getters (métodos de acesso) and setters (métodos de alteração) em qualquer objeto interno padrão ou objeto definido pelo usuário que ofereça suporte à adição de novas propriedades. A sintaxe para definir getters e setters usa a sintaxe literal do objeto.

get

Vincula uma propriedade de objeto a uma função que será chamada quando essa propriedade é requisitada.

set
Vincula uma propriedade de objeto a uma função a ser chamada quando há uma tentativa de definir essa propriedade.

Sintax dos métodos de funções

Nota: Definições de métodos são tecnologias experimentais, parte da proposta do ECMAScript 6, e ainda não são amplamente suportados pelos navegadores.

Começando com ECMAScript 6, você é capaz de definir métodos próprios em uma sintaxe mais curta, semelhante aos getters e setters. Veja method definitions para mais informações.

var obj = {
  foo() {},
  bar() {}
};

Function constructor vs. function declaration vs. function expression

Compare o seguinte:

Uma função definida com function constructor atribuiída à variável multiply

function multiply(x, y) {
   return x * y;
}

Uma function expression de uma função anônima atribuída à variável multiplicar

var multiply = function(x, y) {
   return x * y;
};

Uma function expression de uma função chamada func_name atribuída à variável multiplicar

var multiply = function func_name(x, y) {
   return x * y;
};

Diferenças

Todas fazem aproximadamente a mesma coisa, com algumas diferenças sutis:

Há uma distinção entre o nome da função ea variável à qual a função é atribuída. O nome da função não pode ser alterado, enquanto a variável à qual a função está atribuída pode ser reatribuída. O nome da função pode ser usado somente dentro do corpo da função. A tentativa de usá-lo fora do corpo da função resulta em um error (ou undefined se o nome da função foi declarado anteriormente por meio de uma declaração de variável). Por exemplo:

var y = function x() {};
alert(x); // throws an error

The function name also appears when the function is serialized via Function's toString method.

On the other hand, the variable the function is assigned to is limited only by its scope, which is guaranteed to include the scope where the function is declared in.

As the 4th example shows, the function name can be different from the variable the function is assigned to. They have no relation to each other.A function declaration also creates a variable with the same name as the function name. Thus, unlike those defined by function expressions, functions defined by function declarations can be accessed by their name in the scope they were defined in:

A function defined by 'new Function' does not have a function name. However, in the SpiderMonkey JavaScript engine, the serialized form of the function shows as if it has the name "anonymous". For example, alert(new Function()) outputs:

function anonymous() {
}

Since the function actually does not have a name, anonymous is not a variable that can be accessed within the function. For example, the following would result in an error:

var foo = new Function("alert(anonymous);");
foo();

Unlike functions defined by function expressions or by the Function constructor, a function defined by a function declaration can be used before the function declaration itself. For example:

foo(); // alerts FOO!
function foo() {
   alert('FOO!');
}

A function defined by a function expression inherits the current scope. That is, the function forms a closure. On the other hand, a function defined by a Function constructor does not inherit any scope other than the global scope (which all functions inherit).

Functions defined by function expressions and function declarations are parsed only once, while those defined by the Function constructor are not. That is, the function body string passed to the Function constructor must be parsed each and every time the constructor is called. Although a function expression creates a closure every time, the function body is not reparsed, so function expressions are still faster than "new Function(...)". Therefore the Function constructor should generally be avoided whenever possible.

It should be noted, however, that function expressions and function declarations nested within the function generated by parsing a Function constructor 's string aren't parsed repeatedly. For example:

var foo = (new Function("var bar = \'FOO!\';\nreturn(function() {\n\talert(bar);\n});"))();
foo(); // The segment "function() {\n\talert(bar);\n}" of the function body string is not re-parsed.

A function declaration is very easily (and often unintentionally) turned into a function expression. A function declaration ceases to be one when it either:

  • becomes part of an expression
  • is no longer a "source element" of a function or the script itself. A "source element" is a non-nested statement in the script or a function body:
var x = 0;               // source element
if (x == 0) {            // source element
   x = 10;               // not a source element
   function boo() {}     // not a source element
}
function foo() {         // source element
   var y = 20;           // source element
   function bar() {}     // source element
   while (y == 10) {     // source element
      function blah() {} // not a source element
      y++;               // not a source element
   }
}

Examples

// function declaration
function foo() {}

// function expression
(function bar() {})

// function expression
x = function hello() {}


if (x) {
   // function expression
   function world() {}
}


// function declaration
function a() {
   // function declaration
   function b() {}
   if (0) {
      // function expression
      function c() {}
   }
}

Conditionally defining a function

Functions can be conditionally defined using either //function statements// (an allowed extension to the ECMA-262 Edition 3 standard) or the Function constructor. Please note that such function statements are no longer allowed in ES5 strict. Additionally, this feature does not work consistently cross-browser, so you should not rely on it.

In the following script, the zero function is never defined and cannot be invoked, because 'if (0)' evaluates its condition to false:

if (0) {
   function zero() {
      document.writeln("This is zero.");
   }
}

If the script is changed so that the condition becomes 'if (1)', function zero is defined.

Note: Although this kind of function looks like a function declaration, it is actually an expression (or statement), since it is nested within another statement. See differences between function declarations and function expressions.

Note: Some JavaScript engines, not including SpiderMonkey, incorrectly treat any function expression with a name as a function definition. This would lead to zero being defined, even with the always-false if condition. A safer way to define functions conditionally is to define the function anonymously and assign it to a variable:

if (0) {
   var zero = function() {
      document.writeln("This is zero.");
   }
}

Examples

Example: Returning a formatted number

The following function returns a string containing the formatted representation of a number padded with leading zeros.

// This function returns a string padded with leading zeros
function padZeros(num, totalLen) {
   var numStr = num.toString();             // Initialize return value as string
   var numZeros = totalLen - numStr.length; // Calculate no. of zeros
   for (var i = 1; i <= numZeros; i++) {
      numStr = "0" + numStr;
   }
   return numStr;
}

The following statements call the padZeros function.

var result;
result = padZeros(42,4); // returns "0042"
result = padZeros(42,2); // returns "42"
result = padZeros(5,4);  // returns "0005" 

Example: Determining whether a function exists

You can determine whether a function exists by using the typeof operator. In the following example, a test is peformed to determine if the window object has a property called noFunc that is a function. If so, it is used; otherwise some other action is taken.

 if ('function' == typeof window.noFunc) {
   // use noFunc()
 } else {
   // do something else
 }

Note that in the if test, a reference to noFunc is used—there are no brackets "()" after the function name so the actual function is not called.

Specifications

Specification Status Comment
ECMAScript 1st Edition. Standard Initial definition. Implemented in JavaScript 1.0
ECMAScript 5.1 (ECMA-262)
The definition of 'Function Definition' in that specification.
Padrão  
ECMAScript 2015 (6th Edition, ECMA-262)
The definition of 'Function definitions' in that specification.
Padrão New: Arrow functions, Generator functions, default parameters, rest parameters

Browser compatibility

Feature Chrome Firefox (Gecko) Internet Explorer Opera Safari
Basic support (Yes) (Yes) (Yes) (Yes) (Yes)
Feature Android Chrome for Android Firefox Mobile (Gecko) IE Mobile Opera Mobile Safari Mobile
Basic support (Yes) (Yes) (Yes) (Yes) (Yes) (Yes)

See also

Etiquetas do documento e colaboradores

 Última atualização por: rafaelbertelli,