I detta första arbetspass ska vi bara syssla med raka program, det vill säga varken loopar (uppgift 10 innehåller dock en for-loop) eller funktioner. Det blir in- och utmatning och tilldelningssatser. Här en lista över vad du ska behärska efter detta arbetspass: Hur enkla variabler fungerar. Vilka variabelnamn som är tillåtna. Skillnaden mellan int och float. För det mesta används i denna kurs int, men float kan ibland vara nödvändig. Tilldelningssatsen. Du måste känna till de aritmetiska operatorerna (+,-,/,*) och deras prioritet. Skillnaden mellan heltals- och flyttalsdivision. Och hur modulo % fungerar. if - else. Hur man skriver logiska uttryck med hjälp av de relationsoperatorerna &&,,!. Allt detta hittar du i kapitlen 1 och 2 och fram till sidan 61 i kapitel 3 i boken C genom ett nyckelhål. Pseudokod Ett första steg i lösandet av en uppgift kan vara att försöka skriva ned hur programmet ska fungera i ett talat språk. Tanken är inte att pseudokoden ska vara exakt på något sätt, utan tjäna som ett stöd när programmet sedan ska kodas i C. Om man inte lyckas beskriva, på till exempel svenska, hur programmet ska fungera är det knappast troligt att man kan skriva det i C! Ta därför för vana att rita och skriva ned dina idéer på papper innan du sätter igång. I den här kursen ger vi ofta ett förslag till detta här kallad pseudokod. Arbetets gång I varje arbetspass finns ett antal uppgifter, i stil med dem som kan förekomma på en tentamen. För att få bästa utbyte från dessa måste du försöka lösa dem innan du studerar lösningsförslagen. Totalt kommer Du här, under kursens gång, att få 140 problem med kommenterade lösningar presenterade. Tillsammans med de cirka 150 uppgifter som finns i boken är det mer än tillräckligt. Läs problemtexten noga, helst två gånger. Se till att du förstår vad som efterfrågas. Skriv ned i punkter, på svenska, steg för steg, hur programmet ska fungera. Det behöver inte var mer detaljerat än att du kan följa dina egna noteringar. Om du inte kommer på någon lösning eller inte har fått några uppslag, gå då till avdelningen Pseudokod och tips När du har en klar bild över hur programmet ska fungera, på papper eller i huvudet, är det dags att koda idéerna i C. Håkan Strömberg 1 KTH STH
Det är ofta en bra idé att bygga programmet successivt, med kompileringar lite då och då. Använd också extra printf-satser för att skriva ut mellanresultat. Satser som du sedan tar bort. Ett program är nödvändigtvis inte korrekt för att det ger rätt svar för testexemplet. Under Lösningsförslag hittar du ett kommenterat program. Titta igenom det även om du anser att ditt program är korrekt. Kanske har du hittat en snyggare lösning, eller så kan det finnas värdefulla tips här. Försök komma på varför du inte redan klarat den här kursen. Kanske beror det på att du inte är tillräckligt bekväm med datorn och utvecklingsmiljön, CodeBlocks. I så fall är det speciellt viktigt att du skriver många program, så att du till slut blir trygg med detta. Kanske har du svårt att lösa problemen, hitta en idé. I så fall är det extra viktigt att du läser och förstår problemen. När du funnit en lösning är det kanske inte nödvändigt att koda den varje gång. Håkan Strömberg 2 KTH STH
Uppgifter att lösa Uppgift 1 Olika trianglar Skriv ett program som tar emot uppgifter om längden hos sidorna hos en triangel och avgör vilken av följande typ av triangel det handlar om Typ Liksidig triangel Likbent triangel Annan triangel Ingen triangfel Om en triangel passar in i flera av typerna ovan skall den översta av dessa väljas. En liksidig triangel är förstås också en likbent triangel och även en annan triangel, men ska klassas som liksidig. Tre körningsexempel: Sida A? 34 Sida A? 8 Sida A? 14 Sida B? 10 Sida B? 8 Sida B? 14 Sida C? 34 Sida C? 8 Sida C? 30 Triangeln är likbent Triangeln är liksidig Ingen triangel Ordningen i vilken sidornas längder matas in är inte definierad. Alla indata är heltal. Håkan Strömberg 3 KTH STH
Uppgift 2 Barnomsorg Barnomsorgsavgiften i en kommun beräknas enligt följande: Avgift för barn 1 beräknas till 10% av familjens sammanlagda månadsinkomst Avgift för barn 2 beräknas till 2% av familjens sammanlagda månadsinkomst För varje ytterligare barn ökas avgiften med 1% av månadsinkomsten Den totala avgiftens undre gräns är 400 kronor oavsett antalet barn (förutom inga barn alls) Den totala avgiftens övre gräns är 3500 kronor oavsett antalet barn Skriv ett program som läser in uppgift om antal barn samt månadsinkomst för en familj och skriver ut familjens avgift för barnomsorg, korrekt avrundat till hela kronor. Ett par körningsexempel: Antal barn? 4 Månadsinkomst? 20756 Barnomsorgsavgiften blir 2906 kr Antal barn? 3 Månadsinkomst? 30000 Barnomsorgsavgiften blir 3500 kr Håkan Strömberg 4 KTH STH
Uppgift 3 Hinkarna Figur 1.1: I figur 1.1 ser vi fyra hinkar, A,B,C och D, som från början innehåller ett bestämt antal liter vatten. Man häller nu vatten mellan hinkarna enligt följande: Först häller man från hink A till hinkarna B,C och D. Varje gång lika många liter som det redan finns i den mottagande hinken. I steg två häller man från hink B till hinkarna A,C och D. Varje gång lika mycket som det redan finns i den mottagande hinken. I steg tre är det hink C som ska ge ifrån sig lika många liter till A,B och D, som det redan finns i den mottagande hinken. Till sist häller man från D till A,B och C på samma sätt. Lika mycket som det redan finns i mottagande hink. Skriv ett program som frågar efter hur mycket hinkarna innehåller från början och som bestämmer och skriver ut hur mycket hinkarna innehåller till slut. Ett körningsexempel: Hink A? 66 Hink B? 34 Hink C? 18 Hink D? 10 Till slut innehåller A=32 B=32 C=32 D=32 Du kan anta att det alltid finns tillräckligt med vatten i den avgivande hinken för att kunna utföra en godkänd hällning. Håkan Strömberg 5 KTH STH
Uppgift 4 Den ändrade rektangeln Figur 1.2: I en rektangel är den längre sidan a meter längre än den kortare. Om man ökar den kortare sidan med b meter och samtidigt minskar den längre med c meter, får man en ny rektangel med samma area. Skriv ett program som tar emot uppgifter om a, b och c och som bestämmer arean hos rektangeln. Alla indata och även arean kan förväntas vara heltal. a? 8 b? 4 c? 5 Arean är 240 Uppgift 5 Jultomten Att få jultomten att besöka ditt hem på julafton kostar pengar! För det första börjar han inte jobba förrän 18:00 och han vill inte arbeta efter 24:00. Här är de timlöner han tillämpar: Från Till Timlön i kr 18:00 21:00 350 21:00 24:00 480 Skriv ett program som tar emot den tid du vill att han ska anlända och hur många minuter han ska vara på plats och därefter skriver ut vad du blir skyldig. Utskriften ska göras med två korrekt avrundade decimaler. Ett körningsexempel: När ska tomten komma (tt mm) : 20 55 Hur länge ska han stanna (min) : 15 Tomten kommer att fakturera dig med 109.17 kr När ska tomten komma (tt mm) : 23 30 Hur länge ska han stanna (min) : 45 Uppdraget kan ej utföras Ankomsttiden skrivs in som två tal med ett mellanslag som åtskiljare (18:34 ges alltså som 18 34). Antalet minuter är alltid ett heltal. Då en förfrågan ligger utanför tomtens arbetstid ska detta meddelas. Håkan Strömberg 6 KTH STH
Uppgift 6 Mobilleverantörerna Att välja mobilleverantör i dagens läge det är inte lätt. Därför ombeds du här att skriva ett program som ska underlätta valet. Vi har att göra med tre leverantörer TALKINAIR, LUR AB och CALLME. Var och en med sina egna priser, för vardager före kl 18 : 00, vardagar efter kl 18 : 00 och även en speciell taxa för lördagar, söndagar och helgdagar. Dessutom tillämpar de en fast månadskostnad. Allt enligt tabellen nedan. Företag Fast kostnad kr/mån Vardagar kr/min Vardagar efter 18:00 kr/min TALKINAIR 100 3.20 1.40 1.40 LUR AB 0 4.00 2.10 2.60 CALLME 200 2.80 1.15 1.25 Lör- och söndagar kr/min Genom följande dialog blir det möjligt att uppskatta månadskostnaden för de tre företagen och föreslå ett av dem, det billigaste. Medelsamtalslängd (i sekunder)... : 30 Samtal/dag Vardag... : 10 Samtal/dag Vardag (efter 18:00)... : 8 Samtal/dag Lördag-Söndag... : 5 TalkInAir billigast med 624.80 kr För att över huvud taget kunna göra denna beräkning, måste vi uppskatta samtalslängden i medeltal i sekunder. Dessutom hur många samtal av varje typ som kommer att ringas under dessa dagar. Vi har koncentrerat oss på oktober 2003 som har 23 vardagar och 8 lör- och söndagar. Uppgift 7 Den saknade punkten Adam är på jakt efter koordinaterna till en rektangel placerad i ett vanligt koordinatsystem, med sidorna parallella med axlarna. Tyvärr har han bara tre punkter. Skriv ett program som tar emot koordinaterna till de tre punkterna, som Adam har, och som bestämmer den fjärde. Alla koordinater är heltal. Punkt 1 x? 30 Punkt 1 y? 20 Punkt 2 x? 10 Punkt 2 y? 10 Punkt 3 x? 10 Punkt 3 y? 20 Punkt 4 x: 30 Punkt 4 y: 10 Håkan Strömberg 7 KTH STH
Figur 1.3: Uppgift 8 Trädgården En trädgårdsarkitekt har designat en modell för fruktträdgårdar, en kvadratisk historia där ett antal äppelträd omgärdar ett antal päronträd. I figur 1.3 ser vi tre storlekar från denna modell, med 2,3 och 4 äppelträd utefter en sida. Skriv ett program som tar emot uppgift om antalet äppelträd utefter en sida och som bestämmer det totala antalet äppel- respektive päronträd i hela trädgården. Ett körningsexempel: Antal äppelträd utefter en sida? 4 Det behövs 12 äppelträd Det behövs 9 päronträd Håkan Strömberg 8 KTH STH
Uppgift 9 Arbitrage Figur 1.4: Vid arbitrage, handel med valutor, kan man ha turen att hitta ett sätt, att växla fram och tillbaka mellan olika valutor, så att man genom detta till slut kommer att få en vinst. Allt beroende på felsatta kurser. Här finns en tabell som anger vad man får betala för en enhet i tre olika valutor: Krona Dollar Euro 1 Krona - 0.13 0.11 1 Dollar 7.81-0.84 1 Euro 9.31 1.19 - För 1 krona får man alltså betala 0.13 dollar och för 1 euro får man betala 9.31 kronor. Skriv ett program som utgår från ett givet belopp i kronor och som sedan testar följande växlingsstrategier Ingen växling alls (alla andra alternativ leder till förlust) Från kronor till dollar och tillbaka till kronor Från kronor till euro och tillbaka till kronor Från kronor till dollar vidare till euro och sedan tillbaka till kronor Från kronor till euro vidare till dollar och sedan tillbaka till kronor Programmet ska till sist skriva ut vilken strategi som använts för att nå största möjliga vinst och hur stort det slutliga beloppet då blir. Ett körningsexempel: Belopp i kronor? 1000 Maxbelopp 1024.10 kronor genom att växla K->E->K OBS: Talen i tabellen ska ingå i programkoden på ett sådant sätt att de enkelt, på ett ställe, kan ändras vid testkörning. Håkan Strömberg 9 KTH STH
Uppgift 10 Påskdagen Vi har just firat påsk och med anledning av det, ska vi titta närmare på hur man beräknar vilket datum påskdagen inträffar ett givet år. Här följer algoritmen. T är det givna året och M och D är den eftersökta månaden respektive dagen. Här betyder Q(a/b) heltalsdivision, till exempel Q(13/5) = 2 och R(a/b) resten vid division av a/b, till exempel R(13/5) = 3. k = Q(T/100) a = R(T/19) p = Q((13+8k)/25) b = R(T/4) q = Q(k/4) c = R(T/7) m = R((15 p+k q)/30) d = R((19a+m)/30) n = R((4+k q)/7) e = R((2b+4c+6d+n)/7) Till sist avgörs det hela genom följande villkor: Om d+e 9 så är D = 22+d+e och M = 3 Om d = 29 och e = 6 så är D = 19 och M = 4 Om d = 28 och e = 6 och a > 10 så är D = 18 och M = 4 Annars är D = d+e 9 och M = 4 Skriv ett program som listar datum för påskdagen från 1990 till 2010. Som test vet vi att påskdagen år 2000 inträffade den 23 april. Håkan Strömberg 10 KTH STH
Pseudokod Uppgift 1 Först måste man komma på, att om en sida är längre än summan av de andra två, så kan man inte bilda någon triangel. Därför måste man ta reda på vilken av sidorna som är längst och jämföra den med summan av de två andra. Skriv ut Sida A? Ta emot uppgift om sida A Sätt denna sida till max Skriv ut Sida B? Ta emot uppgift om sida B Om denna sida är längre än max Sätt denna sida till max Skriv ut Sida C? Ta emot uppgift om sida C Om denna sida är längre än max Sätt denna sida till max Om A+B+C < 2 max Skriv ut Ingen triangel Annars Om A = B och A = C Skriv ut Triangeln liksidig Annars Om A = B eller A = C eller B = C Skriv ut Triangeln likbent Annars Skriv ut Annan triangel En något överarbetad pseudokod. Skriver man ner programmet direkt måste man likväl tänka alla dessa tankar. Uppgift 2 Ta emot uppgift om antalet barn, barn Ta emot uppgift om månadslön, inkomst Om antalet barn 1 bestäm avgiften genom 0.1 inkomst Om antalet barn 2 öka på avgiften med 0.02 inkomst Om antalet barn > 2 öka ytterligare på avgiften med 0.01 (barn 2) inkomst Om avgiften är < 400 sätt avgiften till 400 Om avgiften är > 3500 sätt avgiften till 3500 Skriv ut avgiften Håkan Strömberg 11 KTH STH
Uppgift 3 Ta emot uppgift om innehållet i hink A Ta emot uppgift om innehållet i hink B Ta emot uppgift om innehållet i hink C Ta emot uppgift om innehållet i hink D Från A till de övriga Häll från A till B betyder att B = 2 B Häll från A till C betyder att C = 2 C Häll från A till D betyder att D = 2 D Kvar i A är nu A = A B+C+D 2 Vi dividerar med 2 eftersom det är de nya innehållet i B,C,D vi räknar med Häll nu från B till de andra, i fyra steg, på samma sätt Häll nu från C till de andra, i fyra steg, på samma sätt Häll nu från D till de andra, i fyra steg, på samma sätt Skriv ut resultatet Uppgift 4 Ett program som kräver mer kunskaper i matematik än färdigheter i programmering. Antag att den den kortare sidan i rektangeln är x. Då är den andra sidan x + a. Om vi ökar den kortare med b får vi x+b och minskar den längre med c får vi x+a c. Eftersom de två rektanglarna har samma area får vi ekvationen x(x+a) = (x+b)(x+a c) Löser vi ekvationen med avseende på x får vi x = b a c c b Läs in värden på sidornas längder a,b och c Använd formeln för att bestämma x Skriv ut resultatet Håkan Strömberg 12 KTH STH
Uppgift 5 Läs in när tomten ska komma, tim och min Läs in hur länge han ska stanna, tid Timpenningen är konstant. Vi tilldelar två variabler, b1 = 350 och b2 = 480 Vi kommer att räkna allting i minuter och sätter 18 : 00 till 0 Med hjälp av formeln, stid= 60(tim 18)+min, får vi ankomsttiden översatt till minuter efter 18 : 00 Nu kan vi räkna ut tiden då tomten är klar, atid=stid+tid Klockan 21 : 00 är 180 minuter efter klockan 18 : 00 Om de två tidpunkterna ligger utanför 18 : 00 24 : 00 kan tomten inte fullfölja sitt uppdrag Skriv ut Uppdraget kan ej utföras Annars{ Om 180 stid 0 betyder det att tomten gjort hela passet före 21 : 00 Den tid han gått för den lägre timpenningen är då belopp= b1(atid stid) 60 Om 180 stid 0 och 180 atid 0 har tomten arbetat både före och efter 21 : 00 Vi får då följande formel belopp= b1(180 stid) 60 + b2(atid 180) 60 Om 180 stid 0 betyder det att tomten gjort hela passet efter 21 : 00 Den tid han gått för den högre timpenningen är då belopp= b2(atid stid) 60 Skriv ut belopp } Uppgift 6 Med hjälp av formeln där b = f+ l 60 (v vp 23+e ep 23+h hp 8) l Samtalens medellängd i sekunder (indata) v Antalet samtal under vardagar före 18 : 00 (indata) vp Pris kr/min för samtal under vardagar före 18 : 00 (från tabell) e Antalet samtal under vardagar efter 18 : 00 (indata) ep Pris kr/min för samtal under vardagar efter 18 : 00 (från tabell) h Antalet samtal under helger (indata) hp Pris kr/min för samtal under helger (från tabell) kan vi bestämma månadskostnaden för var och en av de tre operatörerna. Ta emot uppgift om samtalets medellängd Ta emot uppgift om antalet samtal under vardagar för 18 : 00 Ta emot uppgift om antalet samtal under vardagar efter 18 : 00 Ta emot uppgift om antalet samtal under helger Använd formeln med uppgifter från indata och tabell för att bestämma kostnaden för de tre operatörerna. Bestäm den lägsta kostnaden och för vilken operatör den gäller Skriv ut operatörens namn och månadskostnaden Håkan Strömberg 13 KTH STH
Uppgift 7 Läs in de sex koordinaterna x 1,y 1, x 2,y 2 x 3,y 3 Jämför två x-koordinater i taget i tre satser. Två måste vara lika. Om till exempel x 1 = x 2 så är den eftersökta x-koordinaten lika med x 3 När man hittat den skriver man ut den Gör nu samma jämförelser med y-koordinaterna Uppgift 8 Programmeringstekniskt inga problem. Det handlar bara om att hitta formlerna äppelträd= 4(appelsida-1) och päronträd= (appelsida 1) 2 Där appelsida står för antalet äppelträd utefter en sida. Uppgift 9 När vi hårdkodar tabellen behöver vi sex olika variabler kd, är en av dem, som står för från kronor till dollar de är en annan, från dollar till euro Vi tilldelar värden till de sex variablerna från tabellen direkt i deklarationen. Ta emot uppgift om beloppet i kronor, belopp En variabel, max, ska till slut innehålla det största belopp kan man få Tilldela max=belopp. Detta är resultatet om man inte gör någon växling alls Tilldela samtidigt val=1. Just nu är det strategi 1 som är bäst. Beräkna nu strategin från kronor till dollar och tillbaka till kronor med b=belopp kd dk Om detta b>max max=b och val=2 Beräkna på liknande sätt b för de övriga tre strategierna och jämför med det hittills högsta beloppet Om val=1 skriver vi ut Växla inte Om val=2 skriver vi ut max tillsammans med K->D->K Skriv ytterligare tre satser som testar val för 3,4,5 och eventuellt skriver ut önskad text Antingen blir det fem if-satser eller en switch-sats. Uppgift 10 När du vet att satserna a=10/3 och b=10%3 ger a=3 och b=1, heltalsdivision och modulo är det bara att koda problemet. En for-loop från 1990 till 2010{ Varje rad i problemtexten leder till en sats i programmet, 10 stycken Q står för heltalsdivision R står för resten vi division, modulo Med hjälp av de fyra villkoren kan vi så till sist bestämma månad och dag som vi för varje varv i loopen skriver ut } Håkan Strömberg 14 KTH STH
Lösningsförslag Uppgift 1 1 #include <stdio.h> 2 int main(void) { 3 int a,b,c,max; 4 printf("sida A? "); 5 scanf("%d",&a); 6 max=a; 7 printf("sida B? "); 8 scanf("%d",&b); 9 if(b>max) 10 max=b; 11 printf("sida C? "); 12 scanf("%d",&c); 13 if(c>max) 14 max=c; 15 if(a+b+c<2*max) 16 printf("ingen triangel\n"); 17 else 18 if(a==b && a==c) 19 printf("triangeln är liksidig\n"); 20 else 21 if(a==b a==c b==c) 22 printf("triangeln är likbent\n"); 23 else 24 printf("annan triangel\n"); 25 } 4-14 Indata. Samtidigt som vi matar in längden av sidorna tar vi reda på den längsta sidan i max. Kan man förstås göra senare i programmet, men det passar bra här. 15-16 En lite klurighet. Om triangelns om omkrets är mindre än 2 gånger den längsta sidan kan man inte bilda någon triangel av de tre sidorna. Till exempel 3,4 och 8. Tänk efter. 18-19 Här tar vi reda på om triangeln är liksidig. Visst kan man jämföra även b och c, men det är onödigt. Tänk efter. 21-22 Här testar vi om triangeln är likbent, om två sidor är lika långa. Tänk på att vi redan filtrerat bort liksidiga trianglar. Om inte heller detta villkor är sant måste det handla om en triangel som varken är liksidig eller likbent. Håkan Strömberg 15 KTH STH
Uppgift 2 1 #include <stdio.h> 2 int main(void) { 3 int barn,inkomst; 4 double avgift; 5 printf("antal barn? "); 6 scanf("%d",&barn); 7 printf("månadsinkomst? "); 8 scanf("%d",&inkomst); 9 if(barn>=1) 10 avgift=0.1*inkomst; 11 if(barn>=2) 12 avgift+=0.02*inkomst; 13 if(barn>2) 14 avgift+=0.01*(barn-2)*inkomst; 15 if(avgift<400.0) 16 avgift=400.0; 17 if(avgift>3500.0) 18 avgift=3500.0; 19 printf("barnomsorgsavgiften blir %.0f kr\n",avgift); 20 } H Ett praktiskt problem med lite matematik, inte alltför svår. 4 Här använder vi double för att deklarera avgift. double är en flyttalstyp med större noggrannhet än float. Det spelar ingen roll här vilken av typerna vi använder. 5-8 Vi läser in data, båda är heltal och därför ska specifikationen vara %d. Ett vanligt fel är att man glömmer &. 9-10 Vi bestämmer avgiften för 1 barn 11-12 Om man har två barn ökar avgiften med en faktor 2%. Man hade lika gärna kunnat skriva avgift=avgift+0.02*inkomst; 13-14 Om man har fler än två barn ökar avgiften med 1% för varje bar utöver två barn 15-16 Om inkomsten är så låg att avgiften inte når upp till 400 kr sätts den till 400 kr. 17-18 Om inkomsten är så hög att avgiften överskrider 3500 kr sätts den till 3500 kr. 19 Avgiften skrivs ut. Med hjälp av specifikationen %.0f får vi den utskriven korrekt avrundad till heltal. Håkan Strömberg 16 KTH STH
Uppgift 3 1 #include <stdio.h> 2 int main(void){ 3 int a,b,c,d; 4 printf("hink A? "); scanf("%d",&a); 5 printf("hink B? "); scanf("%d",&b); 6 printf("hink C? "); scanf("%d",&c); 7 printf("hink D? "); scanf("%d",&d); 8 b=2*b; c=2*c; d=2*d; a=a-(b+c+d)/2; 9 a=2*a; c=2*c; d=2*d; b=b-(a+c+d)/2; 10 a=2*a; b=2*b; d=2*d; c=c-(a+b+d)/2; 11 a=2*a; b=2*b; c=2*c; d=d-(a+b+c)/2; 12 printf("a=%d b=%d c=%d d=%d\n",a,b,c,d); 13 } 4-7 Vi läser in de fyra volymerna. Det är inget som hindrar att man, i C, skriver flera satser på samma rad, något som verkligen använts i detta program. 8-11 Vi häller från en hink i taget, i angiven ordning, och justerar volymen vartefter. 12 Resultatet skrivs ut Uppgift 4 1 #include <stdio.h> 2 int main(void){ 3 int a,b,c,x; 4 printf("a? "); scanf("%d",&a); 5 printf("b? "); scanf("%d",&b); 6 printf("c? "); scanf("%d",&c); 7 x=b*(a-c)/(c-b); 8 printf("arean är %d m^2\n",x*(x+a)); 9 } 7 Här använder vi formeln för att bestämma x 8 Vi skriver ut resultatet. Observera att man kan utför beräkningar direkt i printfsatsen. Vill man inte det måste kan införa en ny variabel,area. Håkan Strömberg 17 KTH STH
Uppgift 5 1 #include <stdio.h> 2 int main(void) { 3 float tot; 4 int stid,atid,tid,tim,min; 5 int b1=350,b2=480; 6 7 printf("när ska tomten komma (tt mm) : "); 8 scanf("%d %d",&tim,&min); 9 printf("hur länge ska han stanna (min) : "); 10 scanf("%d",&tid); 11 12 stid=(tim-18)*60+min; 13 atid=stid+tid; 14 if(stid<0 atid>360) 15 printf("uppdraget kan ej utföras\n"); 16 else { 17 if(180-stid>=0) 18 tot=(atid-stid)*b1/60.0; 19 if(180-stid>=0 && 180-atid<=0) 20 tot=((180-stid)*b1+(atid-180)*b2)/60.0; 21 if(180-stid<=0) 22 tot=(atid-stid)*b2/60.0; 23 printf("tomten kommer att fakturera dig %.2f kr\n",tot); 24 } 25 } 5 Vi hårdkodar timpenningarna. Man kan tilldela en variabel värden i samband med deklarationen. Det är förstås inte nödvändigt, men smidigt om man vill ändra värdena utan att gå igenom hela programmet. 8 Man kan i en scanf-sats ta emot fler än ett värde, bara de två värdena är skilda av ett whitespace, mellanslag eller tab. Normalt gör vi inte det, men är är det påkallat. 12 Vi räknar ut hur många minuter efter klockan 18 : 00 som tomten ska komma. 13 Och hur många minuter efter 18 : 00 han uppfyllt sitt uppdrag. 14-15 Om han ska komma före 18 : 00 eller efter 24 : 00 kan inte uppdraget utföras. 16-24 I annat fall har vi en del olika situationer att ta hänsyn till. Observera måsvingarna på rad 16 och 24 som buntar ihop satserna som hör till else-grenen. 17-18 Hela den tid an uppdraget sträcker sig över är mellan 18 : 00 21 : 00 atid-stid är antalet minuter som tomten stannar. Eftersom lönen är given i kr/tim dividerar vi med 60. 19-20 Den besvärligaste situationen. Tomten kommer för kl 21 : 00 och går efter kl 21 : 00. Vi har då att summera två avgifter. Var och en räknar vi ut på samma sätt som i första fallet. 21-22 I det tredje fallet kommer tomten efter kl 21 : 00. 23 Vi kan nu skriva ut beloppet. Håkan Strömberg 18 KTH STH
Uppgift 6 1 #include <stdio.h> 2 int main(void){ 3 int langd,vanliga,efter18,helg,bolag; 4 float talkinair,lurab,callme,min; 5 printf("samtalslängd i sekunder (medel)... : "); 6 scanf("%d",&langd); 7 printf("samtal/dag Vardag... : "); 8 scanf("%d",&vanliga); 9 printf("samtal/dag Vardag (efer 18:00)... : "); 10 scanf("%d",&efter18); 11 printf("samtal/dag Lördag-Söndag (efer 18:00) : "); 12 scanf("%d",&helg); 13 talkinair=100+langd/60.0*(vanliga*23*3.20+efter18*23*1.40+helg*8*1.40); 14 lurab=0+langd/60.0*(vanliga*23*4.00+efter18*23*2.10+helg*8*2.60); 15 callme=200+langd/60.0*(vanliga*23*2.80+efter18*23*1.15+helg*8*1.25); 16 if (talkinair<lurab){ 17 min=talkinair; 18 bolag=1; 19 } 20 else { 21 min=lurab; 22 bolag=2; 23 } 24 if(callme<min) 25 printf("callme billigast med %.2f kr\n",callme); 26 else 27 if(bolag==1) 28 printf("talkinair billigast med %.2f kr\n",min); 29 else 30 printf("lur AB billigast med %.2f kr\n",min); 31 } H 5-12 Inläsning av data 13-15 Beräkning av månadskostnad för de tre operatörerna. Den formel vi ska använda återfinns vid uppgiftens pseudokod. 16-30 En hel mängd satser krävs sedan för att ta reda på och skriva ut billigaste operatör och tillhörande belopp. Håkan Strömberg 19 KTH STH
Uppgift 7 1 #include <stdio.h> 2 int main(void){ 3 int x1,y1,x2,y2,x3,y3,x4,y4; 4 printf("punkt 1 x? "); scanf("%d",&x1); 5 printf("punkt 1 y? "); scanf("%d",&y1); 6 printf("punkt 2 x? "); scanf("%d",&x2); 7 printf("punkt 2 y? "); scanf("%d",&y2); 8 printf("punkt 3 x? "); scanf("%d",&x3); 9 printf("punkt 3 y? "); scanf("%d",&y3); 10 if(x1==x2) printf("x: %d\n",x3); 11 if(x1==x3) printf("x: %d\n",x2); 12 if(x2==x3) printf("x: %d\n",x1); 13 if(y1==y2) printf("y: %d\n",y3); 14 if(y1==y3) printf("y: %d\n",y2); 15 if(y2==y3) printf("y: %d\n",y1); 16 } 4-9 Vi tar emot 6 koordinater 10-12 Det måste alltid finnas två x-koordinater som är lika. När vi hittat dem, vet vi att den sökta koordinaten är lika med den tredje x-koordinaten. 13-15 På samma sätt kan vi bestämma den saknade y-koordinaten. Uppgift 8 1 #include <stdio.h> 2 int main(void){ 3 int appel,nappel,nparon; 4 printf("antal äppelträd utefter en sida? "); 5 scanf("%d",&appel); 6 nappel=4*(appel-1); 7 nparon=(appel-1)*(appel-1); 8 printf("det behövs %d äppelträd\n",nappel); 9 printf("det behövs %d päronträd\n",nparon); 10 } H En lätt uppgift, där man räknar ut antalet äpplen genom 4 (appel 1) och antal päron genom appel 2. Programmeringen ställer inga krav. Håkan Strömberg 20 KTH STH
Uppgift 9 1 #include <stdio.h> 2 int main(void){ 3 float kd=0.13,ke=0.11,ek=9.31,ed=1.19,dk=7.81,de=0.84; 4 float max=0.0,b,belopp; 5 int val; 6 printf("belopp? "); 7 scanf("%f",&belopp); 8 max=belopp; val=1; 9 b=belopp*kd*dk; 10 if(b>max){max=b; val=2;} 11 b=belopp*ke*ek; 12 if(b>max){max=b; val=3;} 13 b=belopp*kd*de*ek; 14 if(b>max){max=b; val=4;} 15 b=belopp*ke*ed*dk; 16 if(b>max){max=b; val=5;} 17 printf("maxbelopp %.2f kr genom ",max); 18 switch (val){ 19 case 1: printf("att inte växla\n"); break; 20 case 2: printf("att växla K->D->K\n"); break; 21 case 3: printf("att växla K->E->K\n"); break; 22 case 4: printf("att växla K->D->E->K\n"); break; 23 case 5: printf("att växla K->E->D->K\n"); break; 24 } 25 } H Vi utgår alltid från kronor k och har att testa fem olika strategier. 3 Här startar vi med att deklarera de sex situationerna, som vi hämtar från tabellen. kd står för vad man får betala för, i kronor k, för en dollar d, och så vidare. 8 Vi sätter max till det belopp vi har från början och att det bästa är att inte växla alls, val 1 9-10 Första gången växlar vi från kronor till dollar och tillbaka till kronor. Om detta belopp blev större än max har vi ett nytt max och sätter val till 2. 11-12 På samma sätt testar vi nu att växla till euro och tillbaka. 13-16 Här testar vi med samma teknik de återstående strategierna. 17 När man kommer hit vet man vilket som är det största belopp man kan nå upp till och skriver ut det 18-24 Med hjälp av en switch-sats och med hjälp av värdet hos val kan vi nu skriva ut vilken strategi som är bäst. Håkan Strömberg 21 KTH STH
Uppgift 10 1 #include <stdio.h> 2 int main(void) { 3 int T,D,M,k,a,p,b,q,c,m,d,n,e; 4 for(t=1990; T<=2010; T++) { 5 k=t/100; 6 a=t%19; 7 p=(13+8*k)/25; 8 b=t%4; 9 q=k/4; 10 c=t%7; 11 m=(15-p+k-q)%30; 12 d=(19*a+m)%30; 13 n=(4+k-q)%7; 14 e=(2*b+4*c+6*d+n)%7; 15 if(d+e<=9) { 16 D=22+d+e; 17 M=3; 18 } else 19 if(d==29 && e==6) { 20 D=19; 21 M=4; 22 } else 23 if(d==28 && e==6 && a>10) { 24 D=18; 25 M=4; 26 } else { 27 D=d+e-9; 28 M=4; 29 } 30 printf("%4d %2d %2d\n",T,M,D); 31 } 32 } H Här är det viktigt att känna till heltalsdivision och modulo (%). 4-31 En for-loop har smugit sig in, som ska snurra från 1990 till 2010. 5-14 Här är det bara att följa de 10 formlerna som är givna i texten. 15-29 Med hjälp av de villkor, som också är givna i texten kan vi för varje år bestämma månad och dag. 30 För varje varv i loopen skriver vi ut år, månad och dag. Håkan Strömberg 22 KTH STH