ECMAScript 2015, also known as ES6, brought significant changes to the JavaScript language. In this comprehensive guide, we'll explore the most important features that every modern JavaScript developer should know.

Arrow Functions

Arrow functions provide a concise syntax for writing function expressions. They don't have their own this, arguments, super, or new.target.

JavaScript
// Traditional function
function multiply(a, b) {
    return a * b;
}

// Arrow function
const multiply = (a, b) => a * b;

// With single parameter (parentheses optional)
const square = x => x * x;

// With no parameters
const greet = () => console.log('Hello!');

// With multiple statements
const sum = (a, b) => {
    const result = a + b;
    return result;
};

Template Literals

Template literals provide an easy way to create multiline strings and perform string interpolation.

JavaScript
const name = 'Alice';
const age = 28;

// Old way
const greeting = 'Hello, ' + name + '! You are ' + age + ' years old.';

// With template literals
const greeting = `Hello, ${name}! You are ${age} years old.`;

// Multiline strings
const message = `
    This is a multiline
    string in JavaScript.
    No more \\n needed!
`;

Destructuring Assignment

Destructuring allows you to unpack values from arrays or properties from objects into distinct variables.

JavaScript
// Array destructuring
const colors = ['red', 'green', 'blue'];
const [firstColor, secondColor] = colors;
console.log(firstColor); // 'red'

// Object destructuring
const person = {
    name: 'John',
    age: 30,
    city: 'New York'
};
const { name, age } = person;
console.log(name); // 'John'

// With renaming
const { name: personName } = person;
console.log(personName); // 'John'

// Default values
const { country = 'USA' } = person;
console.log(country); // 'USA'

Default Parameters

ES6 allows you to set default values for function parameters.

JavaScript
// Before ES6
function greet(name) {
    name = name || 'Guest';
    console.log('Hello, ' + name);
}

// With ES6 default parameters
function greet(name = 'Guest') {
    console.log(`Hello, ${name}`);
}

greet(); // Hello, Guest
greet('Alice'); // Hello, Alice

Rest and Spread Operators

The rest parameter syntax allows us to represent an indefinite number of arguments as an array.

JavaScript
// Rest parameters
function sum(...numbers) {
    return numbers.reduce((total, num) => total + num, 0);
}
console.log(sum(1, 2, 3, 4)); // 10

// Spread operator with arrays
const arr1 = [1, 2, 3];
const arr2 = [4, 5, 6];
const combined = [...arr1, ...arr2]; // [1, 2, 3, 4, 5, 6]

// Spread operator with objects
const obj1 = { a: 1, b: 2 };
const obj2 = { c: 3, d: 4 };
const merged = { ...obj1, ...obj2 }; // {a: 1, b: 2, c: 3, d: 4}