Menu

Earn Premium with Referrals

Invite your friends and earn Premium rewards through our referral program.

See how it works and start inviting friends.

Top 25 - Part 2
PYTHON

Top 25 - Part 2

Practice the remaining 10 questions from the top 25 Python programming interview questions.

1. What does sys.getrefcount(obj) return for a newly assigned object variable?

Answer: 2 — one reference from the variable, plus one more from the temporary reference created by passing the object into the function.

sys.getrefcount(obj) reports the number of references to an object. But the count is inflated: to even call the function, Python passes obj as an argument, and that call itself creates a temporary reference that exists for the duration of the call.

So for a freshly created object with exactly one variable referencing it:

  • 1 reference from the variable.
  • +1 reference from the argument being passed into getrefcount.

The function reports 2, not 1.

The practical lesson: the absolute number from getrefcount is always at least 1 higher than the “true” count you’d expect, precisely because of the call’s own reference. It’s a debugging tool for understanding reference counting, not an exact census — expect the temporary reference to skew it upward.

2. What will print(“a” “b” “c”) output?

Output: abc

This is string literal concatenation: when two string literals sit next to each other (separated only by whitespace), the Python parser joins them into a single string — at compile time, before the program even runs.

"a" "b" "c" is parsed as the single literal "abc". There are no operators, no commas, no function calls — just adjacency.

The result prints abc.

This feature is used in real code to split long strings across lines for readability, especially in SQL or docstrings. The important caveat: it only works with literals. Variables don’t combine this way — a b is a syntax error, and concatenating variables requires + or f-strings.

3. What is the correct keyword used to modify an outer non-global variable inside a nested function?

Answer: nonlocal.

Python’s scoping rules make a subtle but crucial distinction. Inside a nested function, you can read a variable from an enclosing function without any declaration. But if you try to assign to it, Python assumes you’re creating a new local variable — unless you say otherwise.

  • global declares that a name refers to the module-level (global) scope.
  • nonlocal declares that a name refers to a variable in the nearest enclosing, non-global scope — i.e., an outer function’s local variable.

Example:

def outer():
    x = 10
    def inner():
        nonlocal x
        x = 20
    inner()
    print(x)   # 20 — changed by inner

Without nonlocal, x = 20 inside inner would create a brand-new local x, leaving the outer x untouched.

The interview answer: nonlocal is the keyword for binding to an enclosing (but not global) scope.

4. What is the output of print(round(2.5)) and print(round(3.5)) in Python 3?

Output: 2 and 4

Python 3 uses banker’s rounding — “round half to even.” When a number is exactly halfway between two integers, it rounds to the nearest even integer, rather than always rounding up.

  • 2.5 is halfway between 2 and 3. The even neighbor is 2. Result: 2.
  • 3.5 is halfway between 3 and 4. The even neighbor is 4. Result: 4.

This differs from the common “round half up” convention most people expect from arithmetic. It’s not an accident: rounding half to even avoids the systematic upward bias that plain “round half up” introduces when you sum many rounded numbers — the errors tend to cancel instead of accumulate.

Note this applies to the halfway case. 2.6 rounds to 3 normally, and 2.4 rounds to 2. Only exact halves follow the banker’s rule.

The interview answer: 2 and 4, because Python 3 rounds halves to the nearest even number.

5. Which dunder method is invoked when evaluating len(instance)?

Answer: __len__.

len(obj) doesn’t directly read a size field — it dispatches to the object’s __len__ method.

When you call len(x), Python internally invokes x.__len__() and returns the integer result. This is the protocol pattern that powers most built-in functions: len__len__, str__str__, +__add__, ==__eq__, and so on.

For custom classes, defining __len__ gives you two things at once: len(obj) starts working, and the object becomes truthy/falsy based on its length in boolean contexts (an object with __len__ returning 0 is falsy).

The interview answer: len(instance) calls instance.__len__().

6. What is the result of all([]) vs any([])?

Answer: all([]) is True; any([]) is False.

These are the “vacuous truth” cases — what do you get when there are no elements to check?

  • all(iterable) returns True if every element is truthy. With no elements, there is nothing to violate that claim, so the result is True. It’s the same logic behind the convention that a product over an empty set is 1 — nothing contradicting the condition.
  • any(iterable) returns True if at least one element is truthy. With no elements, there can be no truthy element, so the result is False.

These defaults are chosen so that the functions behave consistently with their mathematical counterparts: all is a universal quantifier (vacuous truth), any is an existential quantifier (empty set → false).

The interview answer: True for all([]), False for any([]).

7. What is the function of the pass keyword in Python?

Answer: pass is a null statement — a syntactic placeholder that does nothing.

Python requires an indented block after certain constructs (if, for, while, def, class, try, …). Sometimes you need the structure but have nothing to put in it yet — stubbing out a class or function, or deliberately doing nothing in an exception handler.

def not_implemented_yet():
    pass

class Placeholder:
    pass

pass fills the block syntactically while executing zero operations. Execution simply moves on.

Contrast with its relatives:

  • continue skips to the next iteration of a loop.
  • break exits the loop entirely.
  • pass does literally nothing — no jump, no exit.

The interview answer: pass is a no-op used where syntax requires a statement but no action is wanted.

8. What will print(3 * ‘2’) display?

Output: 222

The * operator on a string repeats it. '2' * 3 takes the string '2' and concatenates it with itself three times: '222'.

There is no numeric conversion happening. '2' is a string, and string repetition doesn’t turn it into the number 2. The multiplication produces '222' (a string), not 6 (a number).

The symmetry with lists is worth noting: [0] * 3 gives [0, 0, 0], the same repetition idea. The interview answer: '2' * 3 is '222'.

9. What is the main characteristic of a Python set element?

Answer: Elements must be hashable and unique.

A set is implemented with a hash table. That design choice dictates two properties of its elements:

  • Hashable — each element must have a stable hash value so the table can place it. Mutable types like lists and dicts are unhashable and can’t go in a set. Immutable types — int, str, float, tuple (if it contains only hashables) — qualify.
  • Unique — the hash table can’t store the same element twice. Adding an element that’s already present is a silent no-op. This is the set’s whole point: deduplication.

Two consequences follow. Sets are unordered — hash placement determines position, and iteration order isn’t meaningful. And because of hashing, membership checks are O(1) on average, unlike the O(n) linear scan of a list.

The interview answer: set elements must be hashable and unique; sets are unordered and offer fast O(1) membership.

10. What is the result of executing eval(“2 + 3 * 4”)?

Output: 14

eval() takes a string, parses it as a Python expression, and evaluates it.

The expression is 2 + 3 * 4. It follows normal Python operator precedence: multiplication binds tighter than addition, so it’s 2 + (3 * 4) = 2 + 12 = 14.

The output is 14 — the integer result, not the string "2 + 3 * 4".

The deeper point is a warning: eval() runs arbitrary code from a string. If the input isn’t trusted, this is a security hole — eval("__import__('os').system('rm -rf /')") would do exactly what it says. For evaluating user-supplied arithmetic, use ast.literal_eval (safe, literal-only) or parse the expression yourself. The interview answer is 14, with the mental note that eval on untrusted strings is dangerous.

My Private Notes

Notes are auto-saved locally to this device.