← Home

031. String Repetition

Repeat patterns with * operator

031. String Repetition

Building the RAM Manager UI

Aryan’s RAM manager is starting to look real. He wants terminal output that’s easy to scan — separator lines between sections, a banner for the tool name, and a visual progress bar showing how full memory is.

In C he’d write a loop with putchar(). Python’s * operator does it in one shot.

# C-style (don't do this)
sep = ""
for i in range(40):
    sep += "-"

# Python way
sep = "-" * 40

Aryan’s progress bar design: [████████░░░░] where filled blocks show used RAM and empty blocks show free RAM. He wants it to look like htop’s bar.

He writes the functions using a loop in make_separator, forgetting Python has *. Fix it.


💡 Fun fact: String repetition with * is not just syntactic sugar — Python implements it in C under the hood and allocates the full result string in a single memory operation. The loop equivalent using += creates a new string object on every iteration, making it O(n²). For a 10,000-character separator, "-" * 10000 is roughly 5,000 times faster than the loop.

⚠️ Watch out: [[]] * 3 looks like it creates three independent empty lists, but it actually creates three references to the same list. Appending to result[0] also changes result[1] and result[2]. For independent mutable objects, always use a list comprehension: [[] for _ in range(3)].

🤔 Think about it: "x" * 0 returns "" and "x" * -1 also returns "" — negative repetition is silently treated as zero. Is this the right behaviour, or should it raise an error? How does this affect code that dynamically computes the repeat count?

Learning objectives

  • Repeat strings with the * operator
  • Replace loops with * for string repetition
  • Use * for creating separators, progress bars, padding

Key concepts

  • string repetition
  • string building

Try it

Concept detail

The * operator repeats a string: “ab” * 3 = “ababab”. “x” * 0 = “”. It works on any sequence type — strings, lists, tuples.

Why the loop is worse:

  • String concatenation in a loop is O(n²) because each += creates a new string object and copies all previous characters. “x” * n is O(n) — one allocation.
  • For n=10000 chars, the loop does ~50 million character copies; * does 10000.

Warning about list repetition: [0] * 3 creates [0, 0, 0] — three separate integer objects, safe. [[]] * 3 creates THREE REFERENCES to the SAME list! Modifying a[0] also changes a[1] and a[2]. Use a list comprehension instead: [[] for _ in range(3)]

Solution

def make_separator(char, width):
    return char * width

def make_banner(title, width):
    line = "=" * width
    return line + "\n" + title.center(width) + "\n" + line

def make_progress_bar(filled, total):
    filled_char = "" * filled
    empty_char = "" * (total - filled)
    return "[" + filled_char + empty_char + "]"

Tests

def test_separator():
    assert make_separator("-", 5) == "-----"

def test_separator_single():
    assert make_separator("=", 1) == "="

def test_separator_zero():
    assert make_separator("*", 0) == ""

def test_separator_unicode():
    assert make_separator("", 3) == "───"

def test_progress_bar_full():
    assert make_progress_bar(4, 4) == "[████]"

def test_progress_bar_half():
    assert make_progress_bar(2, 4) == "[██░░]"

def test_progress_bar_empty():
    assert make_progress_bar(0, 3) == "[░░░]"

Resources