JavaScript Programming Coding Questions

Practice 30 most asked JavaScript programming coding interview questions with solutions - Easy, Medium, and Hard levels.

1. Print "Hello World" to console

Easy
Output: Hello World
console.log("Hello World");

2. Add two numbers

Easy
Input: a = 10, b = 20
Output: 30
function addNumbers(a, b) {
    return a + b;
}

console.log(addNumbers(10, 20)); // 30

3. Check if number is even or odd

Easy
Input: 7
Output: Odd
function checkEvenOdd(num) {
    return num % 2 === 0 ? "Even" : "Odd";
}

console.log(checkEvenOdd(7)); // Odd

4. Find maximum of two numbers

Easy
Input: 10, 20
Output: 20
function findMax(a, b) {
    return Math.max(a, b);
}

console.log(findMax(10, 20)); // 20

5. Reverse a string

Easy
Input: "Hello"
Output: "olleH"
function reverseString(str) {
    return str.split('').reverse().join('');
}

console.log(reverseString("Hello")); // olleH

6. Check if string is palindrome

Easy
Input: "madam"
Output: true
function isPalindrome(str) {
    const reversed = str.split('').reverse().join('');
    return str === reversed;
}

console.log(isPalindrome("madam")); // true

7. Find factorial of a number

Easy
Input: 5
Output: 120
function factorial(n) {
    if (n === 0 || n === 1) return 1;
    return n * factorial(n - 1);
}

console.log(factorial(5)); // 120

8. Count vowels in a string

Easy
Input: "education"
Output: 5
function countVowels(str) {
    const vowels = 'aeiouAEIOU';
    return str.split('').filter(char => vowels.includes(char)).length;
}

console.log(countVowels("education")); // 5

9. Sum of array elements

Easy
Input: [1, 2, 3, 4, 5]
Output: 15
function sumArray(arr) {
    return arr.reduce((sum, num) => sum + num, 0);
}

console.log(sumArray([1, 2, 3, 4, 5])); // 15

10. Find largest element in array

Easy
Input: [4, 9, 2, 7, 5]
Output: 9
function findLargest(arr) {
    return Math.max(...arr);
}

console.log(findLargest([4, 9, 2, 7, 5])); // 9

11. Remove duplicates from array

Medium
Input: [1, 2, 2, 3, 4, 4, 5]
Output: [1, 2, 3, 4, 5]
function removeDuplicates(arr) {
    return [...new Set(arr)];
}

console.log(removeDuplicates([1, 2, 2, 3, 4, 4, 5])); // [1, 2, 3, 4, 5]

12. Find second largest element in array

Medium
Input: [10, 20, 20, 30, 40]
Output: 30
function findSecondLargest(arr) {
    const unique = [...new Set(arr)].sort((a, b) => b - a);
    return unique[1];
}

console.log(findSecondLargest([10, 20, 20, 30, 40])); // 30

13. Check if two strings are anagrams

Medium
Input: "listen", "silent"
Output: true
function areAnagrams(str1, str2) {
    const sorted1 = str1.split('').sort().join('');
    const sorted2 = str2.split('').sort().join('');
    return sorted1 === sorted2;
}

console.log(areAnagrams("listen", "silent")); // true

14. Flatten nested array

Medium
Input: [1, [2, [3, [4]], 5]]
Output: [1, 2, 3, 4, 5]
function flattenArray(arr) {
    return arr.flat(Infinity);
}

console.log(flattenArray([1, [2, [3, [4]], 5]])); // [1, 2, 3, 4, 5]

15. Find missing number in array (1 to n)

Medium
Input: [1, 2, 4, 5, 6]
Output: 3
function findMissing(arr) {
    const n = arr.length + 1;
    const expectedSum = (n * (n + 1)) / 2;
    const actualSum = arr.reduce((sum, num) => sum + num, 0);
    return expectedSum - actualSum;
}

console.log(findMissing([1, 2, 4, 5, 6])); // 3

16. Rotate array by k positions

Medium
Input: [1, 2, 3, 4, 5], k = 2
Output: [3, 4, 5, 1, 2]
function rotateArray(arr, k) {
    k = k % arr.length;
    return [...arr.slice(k), ...arr.slice(0, k)];
}

console.log(rotateArray([1, 2, 3, 4, 5], 2)); // [3, 4, 5, 1, 2]

17. Find first non-repeating character

Medium
Input: "swiss"
Output: "w"
function firstNonRepeating(str) {
    for (let char of str) {
        if (str.indexOf(char) === str.lastIndexOf(char)) {
            return char;
        }
    }
    return null;
}

console.log(firstNonRepeating("swiss")); // w

18. Count frequency of each element

Medium
Input: [1, 2, 2, 3, 3, 3, 4]
Output: {1: 1, 2: 2, 3: 3, 4: 1}
function countFrequency(arr) {
    return arr.reduce((freq, num) => {
        freq[num] = (freq[num] || 0) + 1;
        return freq;
    }, {});
}

console.log(countFrequency([1, 2, 2, 3, 3, 3, 4])); // {1: 1, 2: 2, 3: 3, 4: 1}

19. Find pairs with given sum

Medium
Input: [1, 2, 3, 4, 5], target = 5
Output: [[1, 4], [2, 3]]
function findPairs(arr, target) {
    const pairs = [];
    const seen = new Set();
    
    for (let num of arr) {
        const complement = target - num;
        if (seen.has(complement)) {
            pairs.push([complement, num]);
        }
        seen.add(num);
    }
    return pairs;
}

console.log(findPairs([1, 2, 3, 4, 5], 5)); // [[1, 4], [2, 3]]

20. Implement debounce function

Medium
Input: function that logs message after 300ms delay
Output: Debounced function
function debounce(func, delay) {
    let timeoutId;
    return function(...args) {
        clearTimeout(timeoutId);
        timeoutId = setTimeout(() => func.apply(this, args), delay);
    };
}

const log = debounce(() => console.log("Hello"), 300);
log(); // Will log after 300ms

21. Implement throttle function

Medium
Input: function that should execute at most once per 1000ms
Output: Throttled function
function throttle(func, limit) {
    let inThrottle;
    return function(...args) {
        if (!inThrottle) {
            func.apply(this, args);
            inThrottle = true;
            setTimeout(() => inThrottle = false, limit);
        }
    };
}

const log = throttle(() => console.log("Hello"), 1000);
log(); // Will execute immediately, then wait 1s

22. Deep clone an object

Medium
Input: {a: 1, b: {c: 2}}
Output: Deep cloned object
function deepClone(obj) {
    if (obj === null || typeof obj !== 'object') return obj;
    
    const clone = Array.isArray(obj) ? [] : {};
    
    for (let key in obj) {
        if (obj.hasOwnProperty(key)) {
            clone[key] = deepClone(obj[key]);
        }
    }
    return clone;
}

const original = {a: 1, b: {c: 2}};
const cloned = deepClone(original);
console.log(cloned); // {a: 1, b: {c: 2}}

23. Implement Promise.all

Hard
Input: Array of promises
Output: Promise that resolves with array of results
function promiseAll(promises) {
    return new Promise((resolve, reject) => {
        const results = [];
        let completed = 0;
        
        promises.forEach((promise, index) => {
            Promise.resolve(promise)
                .then(result => {
                    results[index] = result;
                    completed++;
                    if (completed === promises.length) {
                        resolve(results);
                    }
                })
                .catch(reject);
        });
    });
}

promiseAll([Promise.resolve(1), Promise.resolve(2)])
    .then(console.log); // [1, 2]

24. Implement async/await scheduler with concurrency limit

Hard
Input: Array of async tasks, limit = 2
Output: Execute tasks with max 2 concurrent
class TaskScheduler {
    constructor(limit) {
        this.limit = limit;
        this.queue = [];
        this.running = 0;
    }
    
    async add(task) {
        while (this.running >= this.limit) {
            await new Promise(resolve => this.queue.push(resolve));
        }
        
        this.running++;
        try {
            return await task();
        } finally {
            this.running--;
            const resolve = this.queue.shift();
            if (resolve) resolve();
        }
    }
}

const scheduler = new TaskScheduler(2);
scheduler.add(() => fetch('/api/1'));
scheduler.add(() => fetch('/api/2'));

25. Implement function currying

Hard
Input: curry(add)(1)(2)(3)
Output: 6
function curry(fn) {
    return function curried(...args) {
        if (args.length >= fn.length) {
            return fn.apply(this, args);
        }
        return function(...nextArgs) {
            return curried.apply(this, [...args, ...nextArgs]);
        };
    };
}

const add = (a, b, c) => a + b + c;
const curriedAdd = curry(add);
console.log(curriedAdd(1)(2)(3)); // 6

26. Implement memoization

Hard
Input: Expensive function with repeated calls
Output: Cached results for same inputs
function memoize(fn) {
    const cache = new Map();
    return function(...args) {
        const key = JSON.stringify(args);
        if (cache.has(key)) {
            return cache.get(key);
        }
        const result = fn.apply(this, args);
        cache.set(key, result);
        return result;
    };
}

const fibonacci = memoize(n => {
    if (n <= 1) return n;
    return fibonacci(n - 1) + fibonacci(n - 2);
});

console.log(fibonacci(10)); // 55

27. Implement event emitter

Hard
Input: on(), emit(), off() methods
Output: Working event emitter
class EventEmitter {
    constructor() {
        this.events = {};
    }
    
    on(event, listener) {
        if (!this.events[event]) {
            this.events[event] = [];
        }
        this.events[event].push(listener);
    }
    
    emit(event, ...args) {
        if (this.events[event]) {
            this.events[event].forEach(listener => listener(...args));
        }
    }
    
    off(event, listenerToRemove) {
        if (this.events[event]) {
            this.events[event] = this.events[event]
                .filter(listener => listener !== listenerToRemove);
        }
    }
}

const emitter = new EventEmitter();
emitter.on('greet', name => console.log(`Hello ${name}`));
emitter.emit('greet', 'John'); // Hello John

28. Implement LRU Cache

Hard
Input: capacity = 2, put(1,1), put(2,2), get(1), put(3,3), get(2)
Output: 1, -1 (evicted)
class LRUCache {
    constructor(capacity) {
        this.capacity = capacity;
        this.cache = new Map();
    }
    
    get(key) {
        if (!this.cache.has(key)) return -1;
        const value = this.cache.get(key);
        this.cache.delete(key);
        this.cache.set(key, value);
        return value;
    }
    
    put(key, value) {
        if (this.cache.has(key)) {
            this.cache.delete(key);
        }
        this.cache.set(key, value);
        if (this.cache.size > this.capacity) {
            const firstKey = this.cache.keys().next().value;
            this.cache.delete(firstKey);
        }
    }
}

const lru = new LRUCache(2);
lru.put(1, 1);
lru.put(2, 2);
console.log(lru.get(1)); // 1

29. Flatten object with nested keys

Hard
Input: {a: {b: {c: 1}}}
Output: {"a.b.c": 1}
function flattenObject(obj, prefix = '', result = {}) {
    for (let key in obj) {
        if (obj.hasOwnProperty(key)) {
            const newKey = prefix ? `${prefix}.${key}` : key;
            
            if (typeof obj[key] === 'object' && 
                obj[key] !== null && 
                !Array.isArray(obj[key])) {
                flattenObject(obj[key], newKey, result);
            } else {
                result[newKey] = obj[key];
            }
        }
    }
    return result;
}

const nested = {a: {b: {c: 1}, d: 2}};
console.log(flattenObject(nested)); // {"a.b.c": 1, "a.d": 2}

30. Implement retry logic with exponential backoff

Hard
Input: Async function, maxRetries = 3
Output: Retries with increasing delays
async function retryWithBackoff(fn, maxRetries = 3, delay = 1000) {
    for (let i = 0; i < maxRetries; i++) {
        try {
            return await fn();
        } catch (error) {
            if (i === maxRetries - 1) {
                throw error;
            }
            const backoffDelay = delay * Math.pow(2, i);
            console.log(`Retry ${i + 1} after ${backoffDelay}ms`);
            await new Promise(resolve => setTimeout(resolve, backoffDelay));
        }
    }
}

// Usage
retryWithBackoff(
    () => fetch('https://api.example.com/data'),
    3,
    1000
).then(response => console.log('Success!'))
  .catch(error => console.error('Failed after retries'));