Software Engineer

810 questions | Free

Software Engineer interview questions and answers

For software engineer, developer and programmer roles. Tap a question to see the model answer and what the interviewer is checking.

Most asked Software Engineer interview questions

Q1FresherMost askedPython
Answer

What is the difference between a list and a tuple in Python?

A list is mutable and a tuple is immutable. That is the core difference, and everything else follows from it.

listtuple
Syntax[1, 2, 3](1, 2, 3)
MutableYes (append, remove, assign by index)No
HashableNoYes, if all items are hashable
Use as dict key or set memberNoYes
Typical useHomogeneous collection that changesFixed record, e.g. (x, y) or a function return of several values
  • Tuples are slightly smaller and faster to create, and they signal "this does not change".
  • A tuple containing a list is still not fully frozen: t = (1, [2]) allows t[1].append(3).
  • A single-item tuple needs a comma: (5,).

What they are checking: Whether you know mutability matters (hashing, dict keys), not just the bracket style

Q2FresherMost askedPython
Answer

What are mutable and immutable types in Python? Give examples.

A mutable object can be changed in place after creation, an immutable one cannot. Changing an immutable value really creates a new object.

  • Immutable: int, float, bool, str, tuple, frozenset, bytes.
  • Mutable: list, dict, set, bytearray, and most user-defined class instances.
s = "abc"
print(id(s))
s += "d"          # new string object, id changes
print(id(s))

l = [1, 2]
print(id(l))
l.append(3)       # same object, id unchanged
print(id(l))

Why it matters: Mutable objects can be changed by anyone who holds them. This causes hard-to-find bugs (for example mutable default arguments). Immutable objects are safe to share and can be dict keys.

What they are checking: Understanding of object identity, and what it means for function arguments and hashing

Q3FresherMost askedPython
Answer

What is the difference between `is` and `==` in Python?

== compares values (it calls __eq__). is compares identity: do both names point to the same object in memory?

a = [1, 2]
b = [1, 2]
print(a == b)   # True, equal values
print(a is b)   # False, two different objects
c = a
print(c is a)   # True
  • Use == for value comparison almost always.
  • Use is for singletons: x is None, x is True.
  • Do not use is for numbers or strings. CPython keeps small integers (-5 to 256) and some strings in a cache. So is may seem to work, then fail on larger values.

What they are checking: Whether you avoid the small-integer cache trap and know to use is None

Q4FresherMost askedPython
Answer

What are `*args` and `**kwargs`?

They let a function accept a variable number of arguments. *args collects extra positional arguments into a tuple, and **kwargs collects extra keyword arguments into a dict. The names are convention, the stars are the syntax.

def show(a, *args, **kwargs):
    print(a, args, kwargs)

show(1, 2, 3, x=10, y=20)   # 1 (2, 3) {'x': 10, 'y': 20}

nums = [1, 2, 3]
opts = {"sep": "-"}
print(*nums, **opts)          # unpacking at the call site: 1-2-3

Order in a signature: positional parameters, *args, keyword-only parameters, **kwargs. They are common in decorators and wrappers that must forward any arguments to the wrapped function.

What they are checking: Can you use packing and unpacking, and do you know the parameter order

Q5FresherMost askedPython
Answer

What is a decorator in Python and how does it work?

A decorator is a callable that takes a function and returns a new function. It usually adds work before or after the original call. @decorator above a function is shorthand for func = decorator(func).

import functools, time

def timed(fn):
    @functools.wraps(fn)
    def wrapper(*args, **kwargs):
        start = time.perf_counter()
        try:
            return fn(*args, **kwargs)
        finally:
            print(f"{fn.__name__} took {time.perf_counter() - start:.4f}s")
    return wrapper

@timed
def work(n):
    return sum(range(n))

work(1_000_000)

Points to mention: closures keep a reference to fn. functools.wraps preserves the name and docstring. Decorators are applied at definition time. Typical uses are logging, timing, caching, auth checks and retries.

What they are checking: Closures, first-class functions and whether you remember functools.wraps

Q6FresherMost askedPython
Answer

What are generators in Python? How is `yield` different from `return`?

A generator is a function that contains yield. Calling it returns a generator object (an iterator). It gives values lazily, one at a time. It pauses between values and keeps its local state. return ends the function for good, yield suspends it and can be resumed.

def countdown(n):
    while n > 0:
        yield n
        n -= 1

g = countdown(3)
print(next(g))       # 3
print(list(g))       # [2, 1]
  • Memory use stays small, so generators suit large or endless streams, such as reading a huge file line by line.
  • A generator is exhausted after one pass. Iterating again gives nothing.
  • A generator expression (x*x for x in range(10)) is the compact form.

What they are checking: Lazy evaluation and memory benefits, plus the one-pass trap

Q7FresherMost askedPython
Answer

What is the difference between shallow copy and deep copy?

A shallow copy creates a new outer container but reuses references to the inner objects. A deep copy recursively copies everything, so the result shares nothing with the original.

import copy
a = [[1, 2], [3, 4]]
s = copy.copy(a)        # shallow, same as a[:] or list(a)
d = copy.deepcopy(a)

a[0].append(99)
print(s)   # [[1, 2, 99], [3, 4]]  inner list is shared
print(d)   # [[1, 2], [3, 4]]      independent
  • Plain assignment b = a is not a copy. It is a second name for the same object.
  • Shallow copy is fine for flat structures of immutable items.
  • Deep copy is slower and handles cycles through a memo dict; classes can change it with __deepcopy__.

What they are checking: Whether nested mutable objects are understood, not only the vocabulary

Q8ExperiencedMost askedPython
Answer

What is the GIL and how does it affect multithreading in Python?

The Global Interpreter Lock is a lock in CPython. It lets only one thread run Python bytecode at a time. It protects CPython's internal state, such as reference counts, from race conditions.

Effects:

  • CPU-bound Python code gains no speed from threads, since they take turns on one core.
  • I/O-bound code still benefits, because a thread releases the GIL while waiting on sockets, files or time.sleep.
  • Many C extensions (NumPy, hashing, compression) release the GIL during heavy work.
  • Race conditions on your own data are still possible. You still need locks for steps like counter += 1.

Ways around it: multiprocessing or concurrent.futures.ProcessPoolExecutor for CPU-bound work, asyncio or threads for I/O, native extensions. Python 3.13 added an experimental free-threaded build (PEP 703) where the GIL can be turned off. The default build still has it.

What they are checking: Accurate detail: I/O threads work, CPU threads do not, and the GIL is not a substitute for locks

Q9ExperiencedMost askedPython
Answer

Explain threading vs multiprocessing vs asyncio. When would you use each?

All three give concurrency but with different models.

threadingmultiprocessingasyncio
UnitOS threads, one processSeparate processesCoroutines on one thread
GIL limitYesNo, each process has its ownSingle thread anyway
MemorySharedSeparate (needs pickling or shared memory)Shared
OverheadMediumHighVery low
Best forBlocking I/O with libraries that are not asyncCPU-bound workThousands of concurrent network connections
  • Threading: preemptive switching, so races are possible and locks are needed.
  • Multiprocessing: real parallelism across cores, but data moves through IPC and startup costs more.
  • Asyncio: cooperative; tasks switch only at await, so a blocking call (like requests.get) freezes everything. Use async libraries or asyncio.to_thread.

Rule of thumb: For CPU-bound work use processes. For many network calls use asyncio. For a few blocking calls in old code use a thread pool.

What they are checking: Ability to map a workload to the right concurrency model and know the failure modes

Q10FresherMost askedPython
Answer

What are dunder (magic) methods? Explain `__str__` vs `__repr__`.

Dunder methods are special methods with double underscores. Python calls them to run built-in behaviour: __init__ (construction), __len__ (len()), __getitem__ (indexing), __eq__ (==), __add__ (+), __enter__/__exit__ (with).

__str__ is the readable, user-facing text used by print() and str(). __repr__ is clear text for developers, used in the REPL, logs and containers. It should ideally let you rebuild the object.

class P:
    def __init__(self, x): self.x = x
    def __repr__(self): return f"P(x={self.x!r})"
    def __str__(self): return f"Point at {self.x}"

p = P(3)
print(p)        # Point at 3
print([p])      # [P(x=3)]  containers use repr

If only __repr__ is defined, str() falls back to it, so define __repr__ first.

What they are checking: Operator overloading awareness and the repr/str purpose

Q11FresherMost askedFree with sign-inPython
Answer

How does exception handling work in Python? Explain try, except, else and finally.

Code that may fail goes in try. A matching except handles the error. else runs only if no exception happened. finally always runs, for cleanup.

Q12FresherMost askedFree with sign-inPython
Answer

What is a virtual environment in Python and why do you use one?

A virtual environment is an isolated folder with its own Python and its own installed packages. Each project keeps its own package versions. Other projects and the system Python are not affected.

Q13FresherMost askedFree with sign-inPython
Answer

What is the output of this code, and why? `def add(x, items=[]): items.append(x); return items` called as `add(1)`, `add(2)`.

It returns [1] and then [1, 2]. The default list is created once, when the function is defined, not on each call. So every call without the argument shares the same list.

Q14FresherMost askedFree with sign-inPython
Answer

What are the built-in data types in Python?

Python has these core built-in types:

  • Numeric: int (any size), float, complex, plus bool (a subclass of int).
  • Text: str (immutable Unicode), and binary bytes, bytearray.
  • Sequences: list, tuple, range.
  • Mappings: dict.
  • Sets: set, frozenset.
  • None: NoneType, the single value None.
Q15FresherMost askedFree with sign-inPython
Answer

What does `if __name__ == '__main__':` do?

It runs a block only when the file is run directly (python script.py). It does not run when the file is imported as a module. When Python runs a file as the entry point it sets __name__ to "__main__". When imported, __name__ is the module's name.

Q16ExperiencedMost askedFree with sign-inPython
Answer

Explain async and await in Python. What is an event loop?

async def defines a coroutine. await pauses it until another awaitable finishes. Meanwhile the event loop runs other tasks. The event loop is the scheduler: it runs on a single thread and switches between coroutines at await points.

Q17ExperiencedMost askedScenarioFree with sign-inPython
Answer

A Python function is too slow in production. How do you find and fix the bottleneck?

Measure first, then optimise the part that matters.

Q18ExperiencedMost askedScenarioFree with sign-inPython
Answer

You need to call 100 external APIs and combine the results. How would you do it efficiently?

This is I/O-bound. Run the calls at the same time with asyncio (or a thread pool if the client library is blocking). Also limit how many run at once.

Q19FresherMost askedJavaScript
Answer

What is the difference between var, let and const in JavaScript?

All three declare variables, but they differ in scope, hoisting and reassignment.

varletconst
ScopeFunctionBlockBlock
HoistingHoisted, initialised as undefinedHoisted, but in the temporal dead zone until declaredSame as let
Redeclare in same scopeAllowedErrorError
ReassignYesYesNo
  • const stops reassignment of the binding, not mutation of the value: const a = []; a.push(1) works.
  • Prefer const by default, let when you must reassign, and avoid var in new code.
  • A var declared at the top level of a script becomes a property of the global object; let and const do not.

What they are checking: Whether you understand scope and the temporal dead zone, not only the table

Q20FresherMost askedJavaScript
Answer

What is hoisting in JavaScript?

Hoisting means declarations are processed before the code runs. So names are known in their scope before the line that declares them.

  • var is hoisted and initialised with undefined, so reading it early gives undefined.
  • let and const are hoisted but not initialised. Accessing them before the declaration throws a ReferenceError (the temporal dead zone).
  • Function declarations are hoisted with their body, so you can call them before they appear.
  • Function expressions and arrow functions follow the rule of the variable that holds them.
console.log(a); // undefined
var a = 1;
sayHi();        // works
function sayHi() { console.log("hi"); }
console.log(b); // ReferenceError
let b = 2;

What they are checking: Whether you know the difference between var, let and function hoisting

Q21FresherMost askedJavaScript
Answer

What is a closure? Give a practical example.

A closure is a function together with the variables from the scope where it was created. The function keeps access to those variables even after the outer function has returned.

function makeCounter() {
  let count = 0;
  return () => ++count;
}
const next = makeCounter();
next(); // 1
next(); // 2

count is private: nothing outside can change it except through the returned function.

Common uses: data privacy, function factories, partial application, memoisation, and event handlers or callbacks that remember state. A common trap is capturing a loop variable declared with var. Also, a closure that holds a large object can keep it in memory longer than you expect.

What they are checking: Whether you can explain it simply and name real uses

Q22FresherMost askedJavaScript
Answer

How does the this keyword work in JavaScript?

this is decided by how a function is called, not where it is written. Arrow functions are the exception.

  • Method call obj.fn(): this is obj.
  • Plain call fn(): this is undefined in strict mode and modules, the global object in sloppy mode.
  • new Fn(): this is the new object.
  • call, apply, bind: you set this yourself.
  • Arrow functions have no own this; they use the one from the enclosing scope.
  • In a DOM event handler (regular function), this is the element.
const user = { name: "Asha", hi() { return this.name; } };
user.hi();        // "Asha"
const f = user.hi;
f();              // this lost: undefined or error in strict mode

What they are checking: Whether you can predict this from the call site

Q23FresherMost askedJavaScript
Answer

What is the difference between call, apply and bind?

All three set this for a function. They differ in when the function runs and how arguments are passed.

  • fn.call(thisArg, a, b): runs now, arguments listed one by one.
  • fn.apply(thisArg, [a, b]): runs now, arguments as an array.
  • fn.bind(thisArg, a): does not run; returns a new function with this (and optionally leading arguments) fixed.
function intro(city, country) { return `${this.name}, ${city}, ${country}`; }
const p = { name: "Sita" };
intro.call(p, "Pokhara", "Nepal");
intro.apply(p, ["Pokhara", "Nepal"]);
const bound = intro.bind(p, "Pokhara");
bound("Nepal");

A bound function cannot be re-bound to a different this.

What they are checking: Whether you know each one's timing and argument style

Q24FresherMost askedJavaScript
Answer

What is the difference between == and === in JavaScript?

=== (strict equality) compares value and type with no conversion. == (loose equality) first converts both sides to a common type. This gives unexpected results.

0 == "0"        // true
0 === "0"       // false
null == undefined   // true
null === undefined  // false
NaN === NaN     // false
[] == false     // true

Use === by default. The one accepted use of == is value == null to test for both null and undefined. For NaN use Number.isNaN, and Object.is treats NaN as equal to itself and distinguishes +0 from -0.

What they are checking: Whether you know type coercion and default to strict equality

Q25ExperiencedMost askedJavaScript
Answer

Explain the JavaScript event loop.

JavaScript runs your code on one thread. The event loop is what lets it handle async work without blocking.

  1. Synchronous code runs on the call stack until it is empty.
  2. The host (browser or Node) handles async APIs (timers, network, DOM events). Later it queues a callback.
  3. Promise reactions and queueMicrotask callbacks go to the microtask queue. Timers and I/O callbacks go to the macrotask (task) queue.
  4. When the stack is empty, the loop runs all microtasks. Then it takes one macrotask and runs it. Then it runs microtasks again, and repeats. In browsers rendering happens between tasks.

What this means: a long synchronous loop freezes the page and delays timers. setTimeout(fn, 0) means "after the current code and microtasks". A microtask that keeps adding microtasks can block rendering.

What they are checking: Whether you can describe stack, queues and ordering, not only say single threaded

Q26FresherMost askedJavaScript
Answer

What is the output of this loop, and how do you fix it? for (var i = 0; i < 3; i++) { setTimeout(() => console.log(i), 0); }

It prints 3 3 3.

var is function scoped, so there is one shared i. The timeout callbacks run after the loop ends, when i is already 3.

Fixes:

// 1. let creates a new binding per iteration
for (let i = 0; i < 3; i++) setTimeout(() => console.log(i), 0); // 0 1 2

// 2. IIFE capturing the value
for (var i = 0; i < 3; i++) {
  ((j) => setTimeout(() => console.log(j), 0))(i);
}

This is the classic closure-in-loop question. The key point is that closures capture variables, not values.

What they are checking: Whether you connect closures and scope to a real bug

Q27ExperiencedMost askedJavaScript
Answer

What is the output of this code, and why? console.log('1'); setTimeout(() => console.log('2'), 0); Promise.resolve().then(() => console.log('3')); console.log('4');

Output: 1 4 3 2.

  • 1 and 4 are synchronous, so they run first in order.
  • The promise callback is a microtask, so it runs as soon as the stack is empty: 3.
  • setTimeout is a macrotask, so it runs after the microtasks: 2, even with a delay of 0.

A harder variant adds async function f() { console.log('a'); await null; console.log('b'); }. Code before the first await runs synchronously; the code after it is a microtask. Explain by naming the stack, microtask queue and task queue.

What they are checking: Whether you can trace event loop ordering

Q28FresherMost askedSQL
Answer

What are the different types of SQL joins? Explain with an example.

A join combines rows from two tables on a related column. Take two tables:

employees(id, name, dept_id) and departments(id, dept_name).

JoinReturns
INNER JOINOnly rows that match in both tables
LEFT JOINAll rows from the left table, NULL where the right has no match
RIGHT JOINAll rows from the right table, NULL where the left has no match
FULL OUTER JOINAll rows from both (PostgreSQL yes, MySQL has no direct support)
CROSS JOINEvery combination (cartesian product)
SELECT e.name, d.dept_name
FROM employees e
LEFT JOIN departments d ON d.id = e.dept_id;

This lists every employee, and dept_name is NULL for an employee with no department. With INNER JOIN that employee would disappear. A self join joins a table to itself, for example to find an employee's manager.

What they are checking: Whether you know what happens to unmatched rows, not just the names

Q29FresherMost askedSQL
Answer

What is the difference between WHERE and HAVING?

WHERE filters individual rows before grouping. HAVING filters groups after GROUP BY and can use aggregate functions.

SELECT dept_id, COUNT(*) AS headcount, AVG(salary) AS avg_salary
FROM employees
WHERE salary > 20000          -- row filter, runs first
GROUP BY dept_id
HAVING COUNT(*) > 5;          -- group filter, runs after aggregation
  • WHERE cannot contain aggregates such as COUNT(*) or AVG().
  • Put conditions in WHERE whenever possible, because it reduces rows before grouping and is faster.
  • Logical order: FROM, WHERE, GROUP BY, HAVING, SELECT, ORDER BY, LIMIT.

What they are checking: Understanding of SQL's logical execution order

Q30FresherMost askedSQL
Answer

What is the difference between a primary key and a foreign key?

A primary key uniquely identifies each row in its own table. A foreign key is a column that points to the primary key of another table. It enforces the link between them.

Primary keyForeign key
PurposeIdentify a rowLink to a row in another table
NULLsNot allowedAllowed (unless declared NOT NULL)
DuplicatesNot allowedAllowed
Per tableExactly one (can be composite)Many
CREATE TABLE departments (id INT PRIMARY KEY, name VARCHAR(50));
CREATE TABLE employees (
  id INT PRIMARY KEY,
  name VARCHAR(50),
  dept_id INT,
  FOREIGN KEY (dept_id) REFERENCES departments(id)
);

The foreign key blocks adding an employee with a department that does not exist. It also controls what happens on delete (ON DELETE CASCADE, SET NULL, or restrict).

What they are checking: Referential integrity basics

Q31FresherMost askedSQL
Answer

What is the difference between DELETE, TRUNCATE and DROP?

DELETE removes selected rows, TRUNCATE empties the whole table, DROP removes the table itself.

DELETETRUNCATEDROP
TypeDMLDDLDDL
WHERE clauseYesNoNo
RemovesChosen rowsAll rowsTable and structure
Triggers fireYesNoNo
SpeedSlower (row by row, logged)FastFast
RollbackYesPostgreSQL yes (inside a transaction), MySQL no (implicit commit)MySQL no, PostgreSQL yes in a transaction
DELETE FROM orders WHERE status = 'cancelled';
TRUNCATE TABLE temp_logs;
DROP TABLE temp_logs;

TRUNCATE also resets auto-increment counters in MySQL.

What they are checking: DML vs DDL and the side effects

Q32FresherMost askedSQL
Answer

How do you find the Nth highest salary in SQL?

Use DENSE_RANK so ties are handled correctly, or LIMIT with OFFSET on distinct values.

-- 3rd highest salary (change 3 to N)
SELECT salary
FROM (
  SELECT salary, DENSE_RANK() OVER (ORDER BY salary DESC) AS rnk
  FROM employees
) t
WHERE rnk = 3
LIMIT 1;

Alternative without window functions:

SELECT DISTINCT salary
FROM employees
ORDER BY salary DESC
LIMIT 1 OFFSET 2;   -- OFFSET is N - 1
  • ROW_NUMBER would count tied salaries as separate ranks, which is wrong here.
  • RANK leaves gaps after ties, so the 3rd rank may not exist.
  • If fewer than N distinct salaries exist, both queries return no row.

What they are checking: Handling of ties and knowing rank functions

Q33FresherMost askedSQL
Answer

How do you find the highest salary in each department (max per group)?

Group by department to get just the value. Or join back, or use a window function, to get the full row.

-- Only the max value
SELECT dept_id, MAX(salary) AS max_salary
FROM employees
GROUP BY dept_id;

-- Whole row of the top earner (ties return all)
SELECT e.*
FROM employees e
JOIN (
  SELECT dept_id, MAX(salary) AS max_salary
  FROM employees
  GROUP BY dept_id
) m ON m.dept_id = e.dept_id AND m.max_salary = e.salary;

-- Same with a window function
SELECT * FROM (
  SELECT e.*, RANK() OVER (PARTITION BY dept_id ORDER BY salary DESC) AS rnk
  FROM employees e
) t WHERE rnk = 1;

The common mistake is selecting name together with MAX(salary) in a GROUP BY query. Name is not aggregated, so PostgreSQL rejects it and MySQL with ONLY_FULL_GROUP_BY does too.

What they are checking: The classic 'greatest-n-per-group' pattern

Q34FresherMost askedSQL
Answer

How do you delete duplicate rows from a table while keeping one copy?

Keep the row with the smallest id for each duplicate key and delete the rest.

DELETE FROM contacts
WHERE id NOT IN (
  SELECT min_id FROM (
    SELECT MIN(id) AS min_id
    FROM contacts
    GROUP BY email
  ) keep
);

The extra derived table (keep) is needed in MySQL. MySQL refuses to read and delete from the same table in one subquery. It also works in PostgreSQL.

First find duplicates to verify:

SELECT email, COUNT(*) FROM contacts GROUP BY email HAVING COUNT(*) > 1;

Run it inside a transaction or on a backup first. To prevent the problem permanently, add ALTER TABLE contacts ADD CONSTRAINT uq_email UNIQUE (email);.

What they are checking: Safe data cleanup and prevention

Q35ExperiencedMost askedSQL
Answer

What is a window function? Explain ROW_NUMBER, RANK and DENSE_RANK.

A window function computes a value across a set of rows related to the current row. Unlike GROUP BY, it does not collapse them. You define the set with OVER (PARTITION BY ... ORDER BY ...).

For salaries 90, 80, 80, 70 ordered descending:

SalaryROW_NUMBERRANKDENSE_RANK
90111
80222
80322
70443
  • ROW_NUMBER: unique sequence, ties broken arbitrarily.
  • RANK: ties share a rank, then a gap.
  • DENSE_RANK: ties share a rank, no gap.
SELECT name, dept_id, salary,
       RANK() OVER (PARTITION BY dept_id ORDER BY salary DESC) AS dept_rank
FROM employees;

Other common ones: LAG, LEAD, SUM() OVER, NTILE, FIRST_VALUE.

What they are checking: Whether you know analytics SQL beyond GROUP BY

Q36FresherMost askedSQL
Answer

What is an index and how does it speed up queries? What is the downside?

An index is a separate sorted structure (usually a B-tree). It lets the database find rows without scanning the whole table, like a book index.

CREATE INDEX idx_orders_customer ON orders (customer_id);

Benefits: fast lookups, joins, sorting and range queries on the indexed column.

Costs:

  • Extra disk space.
  • Slower INSERT, UPDATE and DELETE, since every index must be maintained.
  • Too many indexes confuse the planner and waste memory.

Good candidates are columns used in WHERE, JOIN, ORDER BY and foreign keys with high selectivity. Poor candidates are tiny tables and low-cardinality columns such as a boolean. A composite index (a, b) helps queries that filter on a, or on a and b. It does not help a filter on b alone (leftmost prefix rule).

What they are checking: Costs and benefits, not just definitions

Q37FresherMost askedSQL
Answer

Explain ACID properties with an example.

ACID is the set of guarantees of a database transaction.

  • Atomicity: all steps happen or none do.
  • Consistency: a transaction moves the database from one valid state to another, respecting constraints.
  • Isolation: concurrent transactions do not see each other's half-finished work.
  • Durability: once committed, data survives a crash (through the write-ahead log).

Example, transferring 500 from account A to B:

BEGIN;
UPDATE accounts SET balance = balance - 500 WHERE id = 1;
UPDATE accounts SET balance = balance + 500 WHERE id = 2;
COMMIT;

If the second update fails, ROLLBACK restores the first, so money never disappears (atomicity). Constraints such as balance >= 0 keep it consistent. Another session reading mid-transfer does not see a partial state (isolation). After COMMIT a power cut does not lose it (durability).

What they are checking: Concepts tied to a concrete example

Q38FresherMost askedFree with sign-inSQL
Answer

Explain normalization and the first three normal forms.

Normalization organizes tables to reduce redundancy and update anomalies.

Q39ExperiencedMost askedFree with sign-inSQL
Answer

What are the transaction isolation levels and what problems does each prevent?

Isolation levels trade consistency for concurrency. The problems they prevent:

  • Dirty read: reading uncommitted data of another transaction.
  • Non-repeatable read: the same row read twice returns different values.
  • Phantom read: the same query returns new rows the second time.
Q40ExperiencedMost askedScenarioFree with sign-inSQL
Answer

How would you get the top 3 highest-paid employees in every department?

Rank within each department using a window function, then filter.

Software Engineer interview questions by topic