Göm meny

Referenser, objekt, metoder och muterbarhet

Skriv lösningarna till uppgifterna i en och samma fil och testa koden själv innan du använder rättningsskriptet. Att kunna testa sin kod är en viktig del av att programmera!

Att lära dig från uppgifterna

  • Förstå vad metoder är och hur de anropas.
  • Förstå skillnaden mellan muterbara och icke muterbara datatyper i Python.
  • Förstå hur muterbara datastrukturer kan bearbetas i Python, med datatypen list som exempel.

Man kan få max 90 poäng och för att få godkänt krävs 50 poäng (80 för väl godkänt). Försök dock att lösa alla uppgifter då inte alla fel upptäcks av rättningsskriptet. Om ni har lite marginal kan ni kanske bli godkända även om assistenten som rättar hittar något sådant fel.

Uppgift 7.1

Metoder är en särskild typ av funktioner som är inbyggda i objekt och opererar på objektet självt. Vi kommer åt dessa genom att skicka ett meddelande till objektet med hjälp av punktnotation.

Vi har sedan tidigare tittat på sätt att bearbeta strängar med hjälp av funktioner, subskript och loopar. Nu ska vi titta på några strängmetoder, dvs. metoder som finns i alla strängar. Man kan läsa mer om dessa i den officiella pythondokumentationen. String Methods

7.1.1 (5p)

Skriv en funktion first_word(s) som tar in en sträng och returnerar det första ordet i strängen.

Exempel

>>> first_word("hej på dig")
'hej'

7.1.2 (5p)

Skriv en funktion remove_spaces(s) som tar in en sträng och tar bort alla avslutande mellanslag.

Exempel

>>> remove_spaces("Ett annat exempel       ")
'Ett annat exempel'
>>> remove_spaces("   mellanslag i början ska vara kvar.     ")
'   mellanslag i början ska vara kvar.'

7.1.3 (5p)

Skriv en funktion join_list(values) som tar in en lista där elementen är strängar och som returnerar en sträng med : mellan varje element.

Exempel

>>> join_list(["Detta", "är", "ett", "exempel"])
'Detta:är:ett:exempel'

7.1.4 (5p)

Skriv en funktion swap_case(word) som tar en sträng som argument. Om strängen består av endast gemener skall funktionen returnera ordet med versal i början. Om strängen har versal i början men i övrigt består av gemener skall funktionen returnera ordet som endast versaler. Om ordet består av endast versaler skall funktionen returnera ordet med enbart gemener. I övriga fall skall ordet returneras oförändrat. Lös uppgiften med hjälp av strängmetoder och en villkorssats, det är inte tillåtet att iterera över strängen eller accessa enskilda tecken eller delsträngar med subskript (dvs. index eller slice).

Exempel

>>> swap_case('hejsan')
'Hejsan'
>>> swap_case('Hejsan')
'HEJSAN'
>>> swap_case('HEJSAN')
'hejsan'
>>> swap_case('hejSAN')
'hejSAN'
>>> swap_case('HEJsan')
'HEJsan'

Uppgift 7.2

Vi har tidigare tittat på både listor och tupler och betraktat dem som jämförbara med varandra. Nu ska vi dock titta på skillnaden mellan dem. Som ni kanske gissat från kapitlets titel så kommer skillnaden av att listor är föränderliga eller muterbara. Dvs. vi kan lägga till eller ta bort element ur en lista utan att behöva skapa en ny lista.

Den enklaste operation som går att göra med en lista men inte en tupel är att tilldela ett element. Testa att köra följande kod:

1
2
3
4
my_list = [1, 2, 3]
print(f"{my_list=}")
my_list[0] = 42
print(f"{my_list=}")

Prova nu motsvarande med en tupel och notera felmeddelandet:

1
2
3
4
my_tuple = (1, 2, 3)
print(f"{my_tuple=}")
my_tuple[0] = 42
print(f"{my_tuple=}")

Utöver detta finns ett antal metoder för att förändra en lista. Till skillnad från strängmetoder som returnerade en ny lista när ändringar behövde göras så ändrar listmetoderna i en och samma lista. Detta har sina fördelar men inför en ny typ av komplexitet som vi inte stött på tidigare. Du kan läsa om listmetoderna i den officiella pythondokumentationen: More on Lists.

7.2.1 (5p)

Skriv en funktion append_n_to_list(values, a_value) som tar in en lista och ett element och ändrar listan values så att a_value ligger sist. Returnera också den ändrade listan.

Exempel

>>> lst1 = [1, 2, 3, 4, 5, 6]
>>> print(lst1)
[1, 2, 3, 4, 5, 6]
>>> append_n_to_list(lst1,7)
[1, 2, 3, 4, 5, 6, 7]
>>> print(lst1)
[1, 2, 3, 4, 5, 6, 7]

Ledtråd: Använd list-metoden .append(). list.append()

7.2.2 (5p)

Skriv en funktion insert_4_on_index_3(values) som tar in en lista och skjuter in heltalet 4 på index 3 i ursprungslistan. Elementen från och med index 3 ska bli förskjutna med ett steg. Returnera den modifierade listan.

Exempel

>>> lst1 = [1, 2, 3, 5, 6]
>>> print(lst1)
[1, 2, 3, 5, 6]
>>> insert_4_on_index_3(lst1)
[1, 2, 3, 4, 5, 6]
>>> print(lst1)
[1, 2, 3, 4, 5, 6]

Ledtråd: Använd list-metoden .insert(). list.insert()

7.2.3 (5p)

Skriv en funktion extend_list_with_vals(values1, values2) som tar in två listor och lägger elementen från values2 sist i values1. Returnera den ändrade listan.

Exempel

1
2
3
4
5
6
>>> lst1 = [1, 2, 3]
>>> lst2 = [4, 5, 6]
>>> extend_list_with_vals(lst1, lst2)
[1, 2, 3, 4, 5, 6]
>>> print(lst1)
[1, 2, 3, 4, 5, 6]

Ledtråd: Använd list-metoden .extend(). list.insert()

7.2.4 (5p)

Skriv en funktion remove_from_third_in_list(values) som tar bort alla element från och med det tredje elementet i values och returnerar den modifierade listan.

Ledtråd: https://docs.python.org/3/tutorial/datastructures.html#the-del-statement

Exempel

1
2
3
4
5
6
7
>>> lst1 = [1, 2, 3, 5, 6, 7]
>>> print(lst1)
[1, 2, 3, 5, 6]
>>> remove_from_third_in_list(lst1)
[1, 2]
>>> print(lst1)
[1, 2]

Reflektion

Vad är den stora skillnaden mellan strängmetoderna i första uppgiften och listmetoderna i den andra uppgiften?

Ledtråd: Vad hände med objektet till vilket meddelandet skickades? Dvs. värdet motsvarande obj i obj.method().

Uppgift 7.3 (5p)

Skriv funktionen multiply_for_each(values, multiplier) som ändrar och returnerar values med alla värden multiplicerade med multiplier.

OBS! I denna uppgift är det viktigt att du ändrar på listan values och inte skapar en ny lista som du lägger värdena i.

Ledtråd 1: Här använder man lämpligen en loop.

Exempel

>>> lst = [3, 7.1, 3, 1.0]
>>> new_lst = multiply_for_each(lst, 3)
>>> new_lst
[9, 21.3, 9, 3.0]
>>> lst
[9, 21.3, 9, 3.0]

Uppgift 7.4

Skriv en funktion som tar in en lista och byter ordning på alla elementen. Skickar vi in listan [1, 2, 3] ska den ändras till [3, 2, 1]. Funktionen får inte skapa någon ny lista och ska inte heller returnera något. Vi måste alltså spara listan vi skickar till funktionen i en variabel först, så att vi vet att vi modifierar just den listan.

Börja med att implementera swap-funktionen för att byta plats på två element och använd sedan den i reverse_list_*-funktionerna.

7.4.1 (5p)

Skriv en funktion swap(lst, idx1, idx2) som tar en lista och två index och byter plats på värdena på de två indexen. Använd pythons tuple assignment. Funktionen ska inte returnera något.

Ledtråd: I Python kan vi göra följande operation för att tilldela flera referenser samtidigt tupel1 = tupel2 där tupel1 innehåller ett antal referenser och tupel2 samma antal värden eller referenser.

Exempel

>>> menu = ['eggs', 'spam']
>>> swap(menu, 0, 1)
>>> print(menu)
['spam', 'eggs']

7.4.2 (5p)

Skriv funktionen reverse_list_rec(lst) och använd rekursion för att lösa problemet. Lämpligtvis med hjälp av en default-parameter eller inre funktion för att hålla koll på index. Använd swap för att byta plats på element.

Exempel

>>> a = [1, 2, 3, 4, 5, 6, 7]
>>> a
[1, 2, 3, 4, 5, 6, 7]
>>> reverse_list_rec(a)
>>> a
[7, 6, 5, 4, 3, 2, 1]

7.4.3 (5p)

Skriv funktionen reverse_list_iter(lst) och använd en lämplig loop för att lösa problemet. Använd swap för att byta plats på element.

Exempel

>>> a = [1, 2, 3, 4, 5, 6, 7]
>>> print(a)
[1, 2, 3, 4, 5, 6, 7]
>>> reverse_list_iter(a)
>>> print(a)
[7, 6, 5, 4, 3, 2, 1]

När du skapat någon av reverse_list-funktionerna, prova att skicka en tupel till den. Vad händer och förstår du varför?

Tips: Läs felmeddelandet noggrant. Felmeddelanden läses alltid nerifrån och upp eftersom det viktigaste skrivs ut sist (Sidospår: Kommer du ihåg eller kan du räkna ut varför?).

Uppgift 7.5 (10p)

Skriv en funktion make_copy(lst) som tar en lista och skapar en kopia av listan.

Du får inte använda modulen copy eller listmetoden lst.copy.

Tips: Skapa en ny lista och lägg till alla elementen från lst i den.

Exempel

>>> list1 = [1, 2, 3]
>>> list2 = list1
>>> list3 = make_copy(list1)
>>> list1.append(4)
>>> print(list1)
[1, 2, 3, 4]
>>> print(list2)
[1, 2, 3, 4]
>>> print(list3)
[1, 2, 3]

Uppgift 7.6 (10p)

Skriv en funktion update_sequence(seq, string) som tar en sekvens seq (tupel, lista eller sträng) och returnerar sekvensen med string tillagd i slutet. Om seq är muterbar så skall string läggas till i seq. Om seq inte är muterbar så skall en ny sekvens skapas.

Exempel

>>> tuple1 = ('a', 'b', 'c')
>>> tuple2 = update_sequence(tuple1, 'd')
>>> print(tuple1)
('a', 'b', 'c')
>>> print(tuple2)
('a', 'b', 'c', 'd')
>>> list1 = ['a', 'b', 'c']
>>> list2 = update_sequence(list1, 'd')
>>> print(list1)
['a', 'b', 'c', 'd']
>>> print(list2)
['a', 'b', 'c', 'd']

Uppgift 7.7 (10p)

Skriv en funktion make_sentence(words) som tar in en sekvens där elementen är strängar. Funktionen ska returnera en sträng som följer reglerna nedan:

  • Strängen ska inledas med versal.
  • Det ska vara ett mellanslag mellan varje element, förrutom framför skiljetecken (.,:;!?).
  • Det ska vara en punkt på slutet, förrutom ifall sista elementet i words är '...', '!' eller '?'.

Tänk på att vissa skiljetecken kan förekomma mer än en gång i följd.

Exempel

>>> make_sentence(['detta', 'är', 'ett', 'exempel'])
'Detta är ett exempel.'
>>> make_sentence(('är', 'detta', 'en', 'tupel', ':', '(,)', '?'))
'Är detta en tupel: (,)?'
>>> make_sentence(['denna', 'mening', 'har', 'punkt', '.'])
'Denna mening har punkt.'
>>> make_sentence(['denna', 'mening', 'har', 'ellipsis', '...'])
'Denna mening har ellipsis...'

Sidansvarig: Johan Falkenjack
Senast uppdaterad: 2025-08-05