Göm meny
Gäller för: VT26

Pythonuppgifter, kapitel 7. Referenser, objekt, metoder och muterbarhet

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 48 poäng och för att få godkänt krävs 14 poäng. Försök dock att lösa fler 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 (2p)

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 (2p)

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 (2p)

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:

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

Prova nu motsvarande med en tupel och notera felmeddelandet:

1my_tuple = (1, 2, 3)
2print(f"{my_tuple=}")
3my_tuple[0] = 42
4print(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 (2p)

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 (2p)

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>>> lst1 = [1, 2, 3]
2>>> lst2 = [4, 5, 6]
3>>> extend_list_with_vals(lst1, lst2)
4[1, 2, 3, 4, 5, 6]
5>>> print(lst1)
6[1, 2, 3, 4, 5, 6]

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

7.2.4 (2p)

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>>> lst1 = [1, 2, 3, 5, 6, 7]
2>>> print(lst1)
3[1, 2, 3, 5, 6]
4>>> remove_from_third_in_list(lst1)
5[1, 2]
6>>> print(lst1)
7[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 (2p)

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 (2p)

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 (2p)

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...'

Använda rättningsskriptet

OBS! Rättningsskriptet kan bara användas från LiUs Linux-miljö, dvs. är inloggad på en Linux-dator i ett PUL på Campus, har anslutit via VSCodes RemoteSSH, är inloggad på en dator i ett PUL via RDP, eller är inloggad via ThinLinc.

Du kan bara köra rättningsskriptet för ett specifikt kapitel (t.ex. Pythonuppgifter, kapitel 2) en gång var åttonde minut. Detta är för att ni även behöver lära er hur ni testar er egen kod; ni ska inte vara beroende av att det finns ett rättningskript som hjälper er.

Innan du kör rättningsskriptet

Kommentera ut egna testanrop i din kodfil innan du kör rättningsskriptet. Rättningsskriptet kommer att köra din kodfil och om det finns testanrop i filen kan det störa rättningen. Du kan kommentera ut rader i Python genom att ställa dig på raden och trycka Ctrl+’ (tangenten ’ är oftast till höger om Ä på ett svenskt tangentbord) i VS Code. Du kan också markera flera rader och trycka samma tangentkombination för att kommentera ut alla markerade rader.

Köra rättningsskriptet

För att rätta din fil skriver du nedanstående ($ skrivs inte utan representerar prompten i terminalen):

1$ /courses/TDDE44/kursmaterial/pyuppg/pytest.sh <kapitel> <kodfil>
  • Ersätt <kapitel> med det kapitel vars uppgifter koden löser, t.ex. 1 för att rätta kapitel 1, 2 för kapitel 2, osv.
  • Ersätt <kodfil> med namnet på filen som innehåller din kod.
  • OBS! Du måste stå i samma katalog som filen som du vill rätta.
  • OBS! Du får inte döpa din kodfil till ett namn med en punkt i filnamnet utöver punkten innan ändelsen py. Alltså, pyuppg1.py fungerar, pyuppg_kap.1.py fungerar inte.

Exempel

Exempel för Pythonuppgifter kapitel 2 om filen med dina lösningar är döpt till pythonuppg_2.py

1$ /courses/TDDE44/kursmaterial/pyuppg/pytest.sh 2 pythonuppg_2.py

Exempel för Pythonuppgifter kapitel 3 om filen med dina lösningar är döpt till pyuppg3.py

1$ /courses/TDDE44/kursmaterial/pyuppg/pytest.sh 3 pyuppg3.py

Resultat från rättningsskriptet

Rättningsskriptet kommer berätta för dig vilka uppgifter som är godkända, vilka som inte är godkända och vilka som inte hittades. Rättningsskriptet berättar också hur många poäng du fått totalt på hela kapitlet.

När du kör rättningsskriptet kommer du få en utskrift i terminalen som liknar den nedan.

Rättningsskriptet ger ofta viss feedback om vad som är fel. Ni kommer dock ofta själva att behöva felsöka mer i detalj genom att t.ex. lägga till spårutskrifter för att testa koden medan du skriver den.

Exempelutskrift från körning av rättningsskriptet

OBS! Nedanstående utskrift är bara ett exempel på hur utskriften kan se ut. Den är inte kopplad till någon verklig inlämning.

#### POÄNG (100 poäng behövs för GODKÄND UPPG) ####

UPPG 1.1: 5 poäng.
UPPG 1.2: 5 poäng.
UPPG 1.3: 5 poäng.
UPPG 1.4: 5 poäng.
UPPG 1.5: 10 poäng.
UPPG 1.7: 10 poäng.
UPPG 1.8: 10 poäng.
UPPG 1.9: 10 poäng.
UPPG 1.10b: 5 poäng.
UPPG 1.11: 15 poäng.
UPPG 1.12: 15 poäng.


#### SAKNADE UPPGIFTER ####

Kontrollera stavning på din funktioner. Stora och små
bokstäver spelar roll.

UPPG 1.10a saknar funktion: 'first_in_list'
UPPG 1.10c saknar funktion: 'last_in_list'


#### FEL vid TEST ####

Felsök genom att ha testanrop längst ner i din kodfil och
skriv ut resultaten. Kontrollera också så att du har mellanrum
på rätt ställe och att stora/små bokstäver stämmer överrens.

UPPG 1.6: Fel påträffades.

#### ANTAL POÄNG: 95
#### Du är INTE godkänd på Pythonuppgifter 1.
#### 5 poäng saknas.

Skicka in rättningskod

Om uppgiften är godkänd så hittar du även ett stycke med en rättningskod. Detta är en komprimerad version av all data om din lösning och hur många poäng du fått.

Kopiera rättningskoden (se exempel nedan) och klistra in den i en textfil; en fil för varje rättningskod. För laboration 1 kommer du lämna in 3 filer, en för varje kapitel som ingår i första labben. Döp filerna till pyuppg1.txt, pyuppg2.txt och pyuppg3.txt. Motsvarande gäller för labb 2 (kapitel 4-6) och 3 (kapitel 7-9).

------------------------ KOPIERA FRÅN RADEN UNDER DENNA ------------------------
dXBwZzEvaW5mby50eHRVVAkAAz99zVc/fc1XdXgLAAEE9QEAAAQUAAAABcHLEcIgEADQO1VsA3FY
zVd1eAsAAQT1AQAABBQAAABQSwMEFAAAAAgAiIElSZnJPKxkAAAAcgAAABgAHABqb2RmbzAxLXB5
AjhLN2E/iophTDike9+T7dQCwWNePC0+AeaCoWBy89Bfgdcutnt01j4K/FR+qxQY1xzjgbdxud6+
AGpvZGZvMDEtcHl1cHBnMS9taW5pZmllZC5weVVUCQADP33NVz99zVd1eAsAAQT1AQAABBQAAACN
UEsDBAoAAAAAAIiBJUkAAAAAAAAAAAAAAAAQABwAam9kZm8wMS1weXVwcGcxL1VUCQADP33NVz99
kstugzAQRfd8hUU3pCGhRMomUlb9jLayDIzBjbEte4iavy/YPEJaqV0gM3fO3Bk/RGu0RWKZqnQb
VcCJBeysolxcIdmcojEm8SDEnjBWKFwAHyYhv/EAqyrqsJdrt7Jo4DPexo6p4NM5oNgAvTLrsSuT
HZyPM+/j5+OKZbZO2Gi+NJ+VuXZSVsVSKCgssMtqKssqkr+rYTmEwVxXoGUlJn6CPPXL4a4m6Lug
hxIjBdJCSJmwVncKU9W1BViqOTWgjYS78kBkj4Q3KrUqGYLqv/kMXZ66+/Yu37rQlgvrkArVb82N
47rHOd3by0eYEXrz6k86D7Rk/3De5ZO1hBJpeEY/6aDvy0aLEqa0L6xBgR32avQFWq2oYi0kxgIX
X+BS13H/E656EM/rVhPZ33xgH/KzQUQG5/Nvxxs8xl7LExr46Im89g8GoSLFjZhbK5TgAixJGkTj
TllWC2y6Yl/qNpOCo+Y8W7BN9A1QSwMEFAAAAAgAiIElSclUPoaqAAAAqAEAAB8AHABqb2RmbzAx
zZoKdEnH7GDmmeo9xVhT5JpzNVmFaOPAK6G5P1BLAwQUAAAACACIgSVJoN99PmsBAABgAwAAGwAc
LXB5dXBwZzEvcHl1cHBnMXRlc3QubG9nVVQJAAM/fc1XP33NV3V4CwABBPUBAAAEFAAAAOPiUgYC
hQD/wy1+7goahgYGCgX5h5fkpSskpWYc3lZWrJB2eFuRgru/izdQhYtCaECAu6YCSA8XF4itYKhn
aKVgCtWkBxMzwiJmjEXMBIuYqZWCoQG6oBk2QXNsghbYBC2xCRoaJGKx3tAgCatoMjZRoN8NMUWN
CgAAAAAAiIElSQAAAAAAAAAAAAAAABAAGAAAAAAAAAAQAO1BAAAAAGpvZGZvMDEtcHl1cHBnMS9V
VAUAAz99zVd1eAsAAQT1AQAABBQAAABQSwECHgMUAAAACACIgSVJmck8rGQAAAByAAAAGAAYAAAA
AAAAUEsBAh4DFAAAAAgAiIElSaDffT5rAQAAYAMAABsAGAAAAAAAAQAAAKSBAAEAAGpvZGZvMDEt
AAABAAAApIFKAAAAam9kZm8wMS1weXVwcGcxL2luZm8udHh0VVQFAAM/fc1XdXgLAAEE9QEAAAQU
UEQhIezoF+LoAw1noLShKUTYpVTh8BKk8C04vFQhoLIkIz+vtKAgPTOtRMFQkUtBgQsAUEsBAh4D
JUnJVD6GqgAAAKgBAAAfABgAAAAAAAEAAACkgcACAABqb2RmbzAxLXB5dXBwZzEvcHl1cHBnMXRl
cHl1cHBnMS9taW5pZmllZC5weVVUBQADP33NV3V4CwABBPUBAAAEFAAAAFBLAQIeAxQAAAAIAIiB
c3QubG9nVVQFAAM/fc1XdXgLAAEE9QEAAAQUAAAAUEsFBgAAAAAEAAQAegEAAMMDAAAAAA==
------------------------- KOPIERA T.O.M. RADEN OVANFÖR -------------------------

(OBS! Ovanstående rättningskod är ogiltig och bara ett exempel på hur utskriften kommer att se ut).

Inlämning

När Pythonuppgifter, kapitel 4-7 är färdiga är det dags att lämna in.

Inlämningar för Pythonuppgifter behöver inte redovisas innan inlämning.

  • Till varje inlämning av pythonuppgifter ska ni bifoga flera filer. En textfil med rättningskoden för varje kapitel. T.ex. för Pythonuppgifter 1-3 bifogar ni en fil med rättningskoden för kapitel 1, en för kapitel 2 och en för kapitel 3.
  • OBS! Ni ska bara göra EN inlämning av rättningskoder per labb, alla rättningskoder tillhörande samma laboration ska alltså bifogas till samma inlämning.
  • Hur du använder rättningsskripten står längst ner på varje sida med uppgifter.
  • Inlämning av Pythonuppgifter:

Sidansvarig: Johan Falkenjack
Senast uppdaterad: 2026-01-08