Noter til C# Programmering
Alle
sætninger i C# slutter med et semikolon. En sætning kontrollerer sekvensen i
programafviklingen, evaluerer et udtryk eller gør ingenting…
Mellemrum,
tabulatorer og ny linje kaldes under ét for blanktegn. Blanktegn ignoreres af
kompileren. Dvs. at hver gang man laver et mellemrum, så kan man lige så godt
benytte en tabulator eller en ny linje. Blanktegn gør blot koden lettere at
læse.
På
ethvert sted, hvor man kan placere en sætning kan man placere en sammensat
sætning. En sammensat sætning begynder med en venstre-tuborg "{" og
slutter med en højre-tuborg "}". Enhver sætning, som er indeholdt i
en sammensat sætning, skal slutte med et semikolon, medens den sammensatte
sætning selv ikke skal.
Der
findes to generelle typer af operatorer:
·
Aritmetiske
·
Relationelle og logiske
Herunder listes nogle af de aritmetiske
operatorer
Symbol |
Operation |
Eksempel |
Værdi |
+ |
Addition |
3 + 5 |
8 |
‑ |
Subtraktion og fortegn |
43 - 25 |
18 |
* |
Multiplikation |
4 * 7 |
28 |
/ |
Division |
9 / 2 |
4 |
% (heltal) |
Modulus (Restdivision) |
20 % 6 |
2 |
‑ ‑ (postfix) |
Nedskrivning |
6 ‑ ‑ |
5 |
++
(postfix) |
Opskrivning |
6 ++ |
7 |
‑ ‑ (prefix) |
Nedskrivning |
‑ ‑ 6 |
5 |
++
(prefix) |
Opskrivning |
++ 6 |
7 |
Bemærk, at hvis
divisions-operatoren "/" benyttes i forbindelse med to heltal, så
returneres et heltal, idet resten smides bort. (Heltalsdivision)
Eksempel:
int x = 10, y = 3, z;
z =
x/y; // z har nu værdien 3
Det unære
minus (fortegnsminus), multiplicerer den enlige operand med (‑1).
Eksempel:
int x = 10, y;
y =
-x; // y har
nu værdien -10
Bemærk op- og
nedskrivningsoperatorerne (increment og decrement). Disse operatorer var oprindeligt
enestående for C++, og er nu taget med over i Java-sproget og senest C#. Den
kvikke læser kan muligvis nu se, hvordan C++ har fået sit navn, idet C++ er
udviklet på baggrund af sproget C.
Eksempel:
x = x
+ 1;
Kan skrives
som
++x; // præfix opskrivning
eller som
x++; // postfix opskrivning
På samme vis
for nedskrivningsoperatoren. Post- og præfix-notationen giver mulighed for at
påvirke, hvorvidt en op- eller nedskrivning udføres før eller efter at
operanden er evalueret. Betragt de to følgende eksempler:
int x = 10, y;
y =
++x;
// værdien af y er nu 11 og værdien af x er også 11
Variablen x opskrives
ved præfix-notationen før værdien tildeles variablen y.
int x = 10, y;
y =
x++;
// værdien af y er nu 10 og værdien af x er 11
Variablen x opskrives
ved postfix-notationen først efter at dens oprindelige værdi er tildelt
variablen y.
Det er faktisk muligt, at opskrive en
værdi på endnu en måde i C#. Følgende 4 sætninger er ens:
x = x + 1;
x++;
++x;
x += 1;
Det er da forvirrende…?
I lighed med
"selvtildelingsoperatoren" +=, så findes følgende: ‑=, *=, /=,
%=. Disse fungerer som vist:
x -= 1; // Svarer til x = x - 1
x *= 2; // Svarer til x = x * 2
x /= 3; // Svarer til x = x / 3
x %= 4; // Svarer til x = x % 4
Operatorerne
rangordnes som følger:
Rangorden |
Operatorer |
Højst |
( ) |
|
++
‑ ‑ (postfix) |
|
++
‑ ‑ (prefix) |
|
‑ (unært minus) |
|
*
/ % |
|
+
‑ |
Lavest |
= |
Følgende relationelle operatorer
anvendes til sammenligninger:
Symbol |
Betydning |
Eksempel |
Værdi |
< |
Mindre end |
3 < 5 |
Sand |
> |
Større end |
4 > 7 |
Falsk |
<= |
Mindre end eller lig med |
43 <= 25 |
Falsk |
>= |
Større end eller lig med |
9 >= 2 |
Sand |
== |
Lig med |
20 == 6 |
Falsk |
!= |
Forskellig fra |
20 != 6 |
Sand |
Følgende logiske operatorer anvendes:
Symbol |
Betydning |
Eksempel |
Værdi |
&& |
AND |
(3 < 5) && (4 == 4) |
Sand |
|| |
OR |
(3 < 5) || (4 != 4) |
Sand |
! |
NOT |
!(4 == 4) |
Falsk |
Operatorerne
rangordnes som følger:
Rangorden |
Operatorer |
Højst |
! (NOT) |
|
>
>= < <= |
|
==
!= |
|
&& (AND) |
Lavest |
||
(OR) |
Bemærk, at aritmetiske operatorer
rangordnes højere end relationelle og logiske.
Nedenstående
tabel giver et hurtigt overblik over boolsk algebra. To boolske værdier, p og
q, evalueres med NOT, AND, OR og XOR, og resultatet gives. I daglig tale svarer
AND til "både/og", OR svarer til "og/eller", medens XOR
svarer til "enten/eller".
p |
q |
NOT
p |
p
AND q |
p
OR q |
p
XOR q |
Sand |
Sand |
Falsk |
Sand |
Sand |
Falsk |
Sand |
Falsk |
Falsk |
Falsk |
Sand |
Sand |
Falsk |
Sand |
Sand |
Falsk |
Sand |
Sand |
Falsk |
Falsk |
Sand |
Falsk |
Falsk |
Falsk |
XOR (Exclusive OR) findes godt nok
iboende i C#, (^); men man kan også hurtigt lave en metode, der kan foretage en
XOR:
<modifikatorer> bool
xor(bool a, bool
b) {
return (a || b) && !(a && b);
}
Omskrivninger af boolske udtryk vha.
DeMorgans sætning:
Oprindeligt
udtryk |
Omskrevet
udtryk |
NOT p AND NOT q |
NOT(p OR q) |
NOT p AND q |
NOT(p OR NOT q) |
p AND NOT q |
NOT(NOT p OR q) |
p AND q |
NOT(NOT p OR NOT q) |
NOT p OR NOT q |
NOT(p AND
q) |
NOT p OR q |
NOT(p AND NOT q) |
p OR NOT q |
NOT(NOT p AND q) |
p OR q |
NOT(NOT p AND NOT q) |
Hvis man vil benytte DeMorgans sætning
på den logiske operator AND eller den logiske operator OR og to operander, så
skal man negere begge operander bytte om på AND og OR, og sluttelig negere hele
udtrykket.
Programmet
afvikles som nævnt linje for linje i den rækkefølge, som det er skrevet i
koden. if-sætningen
gør det muligt, at evaluere et udtryk, og på baggrund heraf at forgrene
programafviklingen til forskellige dele af koden.
Eksempel:
if (stortTal > lilleTal)
stortTal = lilleTal
Koden sammenligner stortTal
og
lilleTal. Hvis
resultatet er sand, så tildeles variablen stortTal værdien af variablen lilleTal. Herefter
fortsætter programafviklingen sekventielt.
Man
vil ofte have brug for, at programafviklingen forgrener sig til en side, hvis
betingelsen i if-parentesen er sand og til en anden side, hvis den er falsk.
Dette klan naturligvis gøres ved først at teste en situation og dernæst en
anden; men else-nøgleordet giver os mulighed for skrive koden på en lettere
og mere læselig måde.
Eksempel:
int tal1, tal2;
Console.Write("Indtast et stort tal: ");
tal1 = int.Parse(Console.ReadLine());
Console.Write("Indtast et lille tal: ");
tal2 = int.Parse(Console.ReadLine());
if (tal1 > tal2)
Console.WriteLine("Rigtigt!");
else
Console.WriteLine("Ahæm...
det andet tal er størst!");
Console.ReadLine();
Husk,
at sætningen, som afvikles efter at betingelsen i if-parentesen
er evalueret også kan være en sammensat sætning. Denne sætning kan igen bestå
af en if-sætning osv.
Se følgende eksempel på en kompleks indlejret if-sætning:
Eksempel:
int tal1, tal2;
Console.Write("Indtast et tal: ");
tal1 = int.Parse(Console.ReadLine());
Console.Write("Indtast endnu et tal: ");
tal2 = int.Parse(Console.ReadLine());
if (tal1 >= tal2) {
if ((tal1 % tal2)
== 0) {
if (tal1 ==
tal2)
Console.WriteLine("Tallene er ens!");
else
Console.WriteLine("Tallene kan divideres!");
}
else
Console.WriteLine("Tallene
kan ikke divideres!");
}
else
Console.WriteLine("Det
andet tal er størst!");
Console.ReadLine();
Læg mærke til brugen af
tuborg-klammerne. Brugen af disse samt indryk er med til at gøre koden lettere
at læse og forstå. De følgende to eksempler viser, hvorfor brugen af
tuborg-klammer er hensigtsmæssig. Prøv at indtaste kodeeksemplerne og kør dem.
Hvad går galt i det første eksempel?
Eksempel:
int tal;
Console.Write("Indtast et tal: x, hvor x<10 eller x>100: ");
tal = int.Parse(Console.ReadLine());
if (tal > 10)
if (tal <
100)
Console.WriteLine("Tallet
skal være større end 100, tak!");
else
Console.WriteLine("Tallet
skal være mindre end 10, tak!");
Console.ReadLine();
Eksempel:
int tal;
Console.Write("Indtast et tal: x, hvor x<10 eller x>100: ");
tal = int.Parse(Console.ReadLine());
if (tal > 10) {
if (tal <
100)
Console.WriteLine("Tallet
skal være større end 100, tak!");
}
else
Console.WriteLine("Tallet
skal være mindre end 10, tak!");
Console.ReadLine();
if-else-if stigen er en meget anvendt programstruktur, som kan
illustreres vha. af følgende eksempel:
int tal;
Console.Write("Indtast et af flg. tal (0, 1, 2, 3, 4, 5):");
tal = int.Parse(Console.ReadLine());
if (tal == 1) Console.WriteLine("Tallet
er ét");
else if (tal == 2) Console.WriteLine("Tallet
er to");
else if (tal == 3) Console.WriteLine("Tallet
er tre");
else if (tal == 4) Console.WriteLine("Tallet
er fire");
else Console.WriteLine("Tallet er
mindre end 1 eller større end 4");
Console.ReadLine();
Prøv at
indtaste det ovenstående eksempel og kør det! Som man vil se, så afvikles
programmet oppefra og nedefter. Når en betingelse er opfyldt, så afvikles den
tilhørende sætning, og resten af stigen springes over. Hvis ingen betingelser
er opfyldte, så afvikles sætningen, som følger efter det sidste else-nøgleord, og
alle andre sætninger i stigen overspringes
kombinationer
af if og else…if kan blive
meget uoverskuelig, hvis de indlejres i flere niveauer. Heldigvis findes der et
brugbart alternativ i C#: switch, der i modsætning til if tillader,
programafviklingen kan forgrene sig på baggrund af et utal af forskellige
værdier. Herunder er listet et eksempel
Eksempel:
int tal;
Console.Write("Indtast et tal mellem 0 og 4: ");
tal = int.Parse(Console.ReadLine());
switch (number)
{
case 0: Console.WriteLine("Dejligt
rundt tal!");
break; // Spring ud af strukturen
case 4:
case 3:
case 2:
case 1: Console.WriteLine("Positivt!");
break;
default: Console.WriteLine("Uden for
nummer ... desværre!");
break;
}
Brugeren bedes indtaste et tal mellem 1 og 4. I switch-parentesen evalueres tallet. Her kan placeres ethvert gyldigt C#-udtryk. case-sætningerne gennemgås nu oppefra og nedefter i søgen efter et tal som matcher tallet i switch-parentesen, dvs. som er lig med dette tal. Herefter udføres sætningen efter case, eller programmet fortsætter sekventielt indtil et break tvinger programafviklingen ud af strukturen. Hvis ingen case matcher, så afvikles koden under default. Prøv at indtaste det ovenstående eksempel og kør det. Opfører programmet sig, som du forventer?