DEV Community

Cover image for Arrow Functions vs Function Declarations in JavaScript
Jess Alejo
Jess Alejo

Posted on

3

Arrow Functions vs Function Declarations in JavaScript

Okay, so I keep running into this: should I use an arrow function or a function declaration? They both work, but there are some sneaky differences. Let's talk it out.

The Two Approaches

Here’s what I mean. Both of these do the same thing—find a user by id from a list:

Arrow Function Expression

const getUserById = userId => usersFromServer.find(user = user.id === userId);
Enter fullscreen mode Exit fullscreen mode

Function Declaration

function getUserById(userId) {
  return usersFromServer.find(user = user.id === userId);
}
Enter fullscreen mode Exit fullscreen mode

Looks basically the same, right? But nah, there's more going on here.


The Real Differences

1. Syntax & Readability

  • Arrow functions are slick and short, especially for simple stuff. No need for return if it's a one-liner.
  • Function declarations are a little bulkier but sometimes clearer, especially for bigger functions.

2. Hoisting

  • Function declarations? Hoisted. I can use them before they're even written in the code. Magic.
  • Arrow functions? Nope. They exist only after the line they're defined on. Try calling one before, and boom—error.

Example:

const usersFromServer = [{id: 1, name: "Jess"}, {id: 2, name: "Jane"}];

console.log(getUserById(1));

function getUserById(id) {
  return usersFromServer.find(user => user.id === id);
}

//-> {id: 1, name: 'Jess'} ✅ Works fine
Enter fullscreen mode Exit fullscreen mode
const usersFromServer = [{id: 1, name: "Jess"}, {id: 2, name: "Jane"}];

console.log(getUserById(1));

const getUserById = (id) => usersFromServer.find(user => user.id === id);

//-> Uncaught ReferenceError: getUserById is not defined ❌ Error
Enter fullscreen mode Exit fullscreen mode

3. this is Weird

  • Arrow functions don't have their own this. They just borrow it from wherever they're written.
  • Function declarations? They have their own this and change depending on how they're called.

Check this out:

const user = {
  id: 1,
  getId: () => this.id // ❌ 'this' is NOT the user object
}

console.log(user.getId());
//-> undefined
Enter fullscreen mode Exit fullscreen mode

Now compare:

const user = {
  id: 1,
  getId() { return this.id } // ✅ 'this' actually refers to the user object
};

console.log(user.getId());
//-> 1 
Enter fullscreen mode Exit fullscreen mode

See the problem? Arrow functions don't play nice in objects.

4. When to Use What?

Feature Arrow Function Function Declaration
Short & clean? ✅ Yes ❌ Nope
Hoisted? ❌ Nope ✅ Yep
Own this? ❌ Nope (inherits) ✅ Yep (changes dynamically)
Good for objects? ❌ Nope ✅ Yep

So, What's the Verdict?

  • Arrow functions = great for quick, simple stuff, especially when this doesn't matter (like callbacks).
  • Function declarations = better when hoisting or this matters, like object methods.

Final Thought

Honestly, I just use arrow functions whenever possible—unless this starts acting up. Then I switch. Simple as that. 🚀

SurveyJS custom survey software

Simplify data collection in your JS app with a fully integrated form management platform. Includes support for custom question types, skip logic, integrated CCS editor, PDF export, real-time analytics & more. Integrates with any backend system, giving you full control over your data and no user limits.

Learn more

Top comments (4)

Collapse
 
alexmustiere profile image
Alex Mustiere

You could also have mentioned the "function expression" like this:

const getUserById = function(id) {
  return usersFromServer.find(user => user.id === id);
};
Enter fullscreen mode Exit fullscreen mode

The part after the = can be a regular function, it's not mandatory to be an arrow function.
And you can use it like any function:

console.log(getUserById(1));
Enter fullscreen mode Exit fullscreen mode
Collapse
 
jessalejo profile image
Jess Alejo

This verbosity with JavaScript functions sometimes confuses me.

Collapse
 
pengeszikra profile image
Peter Vivo • Edited

imho ordenary function are dangerous!
Before ES6 are initiated the class and arow function, then function is the swiss knife.
That can use for function, and for class also.
You can write a class with function:

function Animal(name, sound) {
  this.name = name;
  this.sound = sound;
  this.makeSound = function() {
      console.log(this.name + " says " + this.sound);
    };
}

var dog = new Animal("Dog", "Woof");
dog.makeSound();

var cat = new Animal("Cat", "Meow");
cat.makeSound();
Enter fullscreen mode Exit fullscreen mode

That why is important to know function is a ghost of our past. And that is the reason why function is handled this a strange way.

Collapse
 
himanshu_code profile image
Himanshu Sorathiya

Nice explanation of this, but for me I use to prefer function declaration more as those 3 4 liner code gives me better understandably of what's happening and what's that function used for even after it's very simple maths evaluation, and that function keyword gives me clear idea that it's a function

Sentry image

See why 4M developers consider Sentry, “not bad.”

Fixing code doesn’t have to be the worst part of your day. Learn how Sentry can help.

Learn more