Python Arena
Step 2 of 5

Strings can't be changed

Many of your tools work on lists and on strings alike: indexes, slices, len, in and for. So it seems natural to change a character of a string the way you change an item of a list. Try it:

scores = [7, 4, 9]
scores[1] = 8
print(scores)
word = "cat"
word[0] = "b"
Output
[7, 8, 9]
Python stops with
Traceback (most recent call last):
  File "main.py", line 5, in <module>
    word[0] = "b"
    ~~~~^^^
TypeError: 'str' object does not support item assignment

The list takes the new item, but the string refuses. Once a string exists, nothing can change it: not a character, not its length, not its order. Strings are immutable. Even sorting works differently: the function sorted leaves the string alone and gives you a new list of its characters in order.

New strings instead

What you can do is build a new string from pieces of the old one, and store it in the same variable:

word = "cat"
word = "b" + word[1:]
print(word)
word = word + "s"
print(word)
print(sorted("cab"))
Output
bat
bats
['a', 'b', 'c']

word[1:] is "at", so "b" + word[1:] is a new string, "bat", and word now refers to it. Nothing happened to the string "cat" itself: word was simply given a different string.

That's why no string method changes the string it's called on. Methods like upper and lower return a new string instead, and the original stays as it was. To keep the result, store it, often in the same variable:

name = "ada"
name.upper()
print(name)
name = name.upper()
print(name)
Output
ada
ADA

The second line makes "ADA" and throws it away, because nothing stores it. A list method like sort is different: it changes the list itself and returns None. So for a list, numbers.sort() alone is right, and for a string, name = name.upper() is.

Your task

Challenge 1 of 3

The program should print the name the user types with its first letter in capitals, but it crashes. Fix it by building a new string instead of changing the old one:

Name: grace
Grace

Challenge 2

Write the function replace_at(text: str, index: int, char: str) -> str, which returns a new string that is like text but has char at the given index. For example, replace_at("table", 0, "c") returns 'cable'. You can assume the index is in the string.

Challenge 3

What does this program print? Type each line it prints.