Essential ES6 Patterns and Features for Modern JavaScript Development

Variable Scoping and Temporal Dead Zone

JavaScript's variable declaration mechanisms underwent significant refinement in ES6. The legacy var keyword exhibits function-scoping and hoisting behavior, where declarations migrate to the top of their containing scope during compilation phase.

console.log(counter); // undefined
var counter = 5;

Conceptually, the runtime interprets this as:

var counter;
console.log(counter); // undefined
counter = 5;

In contrast, let and const establish block-level scoping and introduce the temporal dead zone—a period between scope entry and declaration where accessing the variable triggers a ReferenceError.

console.log(threshold); // ReferenceError: Cannot access 'threshold' before initialization
let threshold = 100;

Additionally, const mandates assignment during declaration and prevents rebinding, though object mutations remain permissible.

Inheritance Mechanisms

Constructor Functions

Prier to ES6, inheritance relied on constructor functions and prototype manipulation:

function Vehicle(type) {
  this.type = type;
}

Vehicle.prototype.getType = function() {
  return this.type;
};

function Car(type, model) {
  Vehicle.call(this, type);
  this.model = model;
}

Car.prototype = Object.create(Vehicle.prototype);
Car.prototype.constructor = Car;

const sedan = new Car('car', 'sedan');
sedan.getType(); // 'car'

This approach requires manual prototype chain setup and loses the constructor reference without explicit correction.

Class Syntax

ES6 classes provide cleaner abstraction over prototypal inheritance:

class Vehicle {
  constructor(type) {
    this.type = type;
  }
  
  getType() {
    return this.type;
  }
}

class Car extends Vehicle {
  constructor(type, model) {
    super(type);
    this.model = model;
  }
}

const suv = new Car('car', 'suv');
console.log(suv instanceof Vehicle); // true

While syntactically distinct, classes internally utilize the same prototype-based delegation model.

Module Architecture

Immediate Invocation Pattern

Pre-ES6 modularization relied on function scoping to encapsulate implementation details:

const utils = (function(global) {
  const privateVar = 'hidden';
  
  function privateMethod() {
    return privateVar;
  }
  
  return {
    expose: privateMethod
  };
})(window);

CommonJS

Server-side environments historically adopted CommonJS:

// math.js
module.exports = {
  calculate: (x, y) => x + y
};

// app.js
const math = require('./math');
console.log(math.calculate(2, 3)); // 5

ES6 Modules

The standardized module system enables static analysis and tree-shaking:

// config.js
export const API_URL = 'https://api.example.com';

// main.js
import { API_URL } from './config.js';
console.log(API_URL);

Proxy for Interception

The Proxy API enables meta-programming through operation interception:

const validator = {
  set(target, prop, value) {
    if (prop === 'age' && typeof value !== 'number') {
      throw new TypeError('Age must be numeric');
    }
    target[prop] = value;
    return true;
  }
};

const person = new Proxy({}, validator);
person.age = 25; // Valid
// person.age = 'twenty'; // Throws TypeError

Array Transformation Methods

Mapping

Transform elements through functional projection:

const measurements = [10, 20, 30];
const tripled = measurements.map(x => x * 3);
// [30, 60, 90]

Filtering

Select subset based on predicates:

const scores = [85, 92, 78, 95];
const passing = scores.filter(s => s >= 80);
// [85, 92, 95]

Reduction

Accumulate values into composite results:

const transactions = [10, -5, 20, -3];
const balance = transactions.reduce((acc, curr) => acc + curr, 0);
// 22

Dictionary Implementations

Plain Objects

Standard objects restrict keys too strings and symbols, lacking guaranteed iteration order and requiring prototype pollution safeguards.

Map Collections

Map structures accept arbitrary key types and preserve insertion sequence:

const userCache = new Map();
userCache.set(101, { name: 'Alice' });
userCache.set(102, { name: 'Bob' });

for (const [id, data] of userCache) {
  console.log(id, data);
}

WeakMap

WeakMap maintains weak references to object keys, enabling private data attachment without preventing garbage collection:

const privateData = new WeakMap();

class SecureBox {
  constructor(secret) {
    privateData.set(this, { secret });
  }
  
  reveal() {
    return privateData.get(this).secret;
  }
}

Tags: javascript ES6 Interview frontend web development

Posted on Sun, 12 Jul 2026 16:28:05 +0000 by sheephat