Voortborduren op eerder gedaan werk Derde poging: “subklassen” class Twee { int x, y; int oud ( ) { return x+y; } class Twee : Twee { Drie int z; } int nieuw ( ) { return x+y+z; } }
Klasse en subklasse class Bolletje { class KleurBol : Bolletje { int x, y, diam; Color kleur; void plaats(int x0, int y0) { this.x = x0; this.y = y0; } void verf(Color k) { this.kleur = k; } override void groei( ) { this.diam++; } void teken(Graphics g) { g.FillEllipse( new Brush(kleur) , x, y, diam, diam ); } virtual void teken(Graphics g) { g.DrawEllipse( Pens.Black , x, y, diam, diam ); } g.DrawEllipse( Pens.Black , x, y, diam, diam ); base.teken(g); } } Bolletje b = new Bolletje(); KleurBol k = new KleurBol(); b = k; b.plaats(10,20); k.plaats(10,20 ); b.teken(gr); b.groei ( ); k.verf( Color.Green ); b.teken(gr); k.teken(gr); k = b; b.verf( Color.Red );
string versus char string char klasse primitief type object-verwijzing directe waarde nul, een of meer… precies één symbool "" "A" "hello" ’A’ operatoren, methoden properties, indexer operatoren == , + == , + , <= Substring, ToUpper Length s[i]
String-methodes int Length bool Equals (string s) string Concat (string s) string Substring (int start) string Substring (int start, int aantal) string ToUpper ( ) string ToLower ( )
Publieksvraag Schrijf een methode Beginstuk met twee string-parameters x en y die bepaalt of x het beginstuk van y is Schrijf een methode Onderdeel met twee string-parameters x en y die bepaalt of x ergens als substring van y voorkomt
Methode Beginstuk kort lang public static bool Beginstuk (string x, string y) { } return x == y . Substring ( 0, x.Length ) ;
Methode Onderdeel public static bool Onderdeel (string x, string y) { } int t; for (t=0; t<y.Length; t++) if ( ) return true; Beginstuk(x, ) y . Substring(t) return false;
Meer string-methodes bool StartsWith (string s) bool EndsWith (string s) int IndexOf (string s) public static bool Onderdeel(string x, string y) { return y.IndexOf(x) >= 0 ; }
string versus array Klasse Type met speciale syntax Indexer -notatie string s = new string(); char[] a = new char[10]; Indexer -notatie Speciale index-notatie c = s[2]; s[3] = c; c = a[2]; a[3] = c; Speciale quote-notatie s = "hallo"; Property s.Length Property a.Length Methoden s.IndexOf(t); s.Substring(3,2);
Publieksvraag // schrijf een static methode die telt hoe // vaak een symbool voorkomt in een string // voorbeeld-aanroep: int n; n = Demo . Freq(’e’, "some text" ); // hint: gebruik een for opdracht
Tel symbool-frequentie public static int Freq(char x, string s) { int aantal; aantal = 0; for (int t=0; t<s.Length; t++) if ( ) aantal++; s[t]==x return aantal; }
Character coding code 0 code 32 code 48 code 65 code 97 code 127
char bijzonderheden alfabetisch geordend char c; if ( ’A’<=c && c<=’Z’ ) … converteerbaar naar int int n; n = c + 32; en terug c = (char) n;
Conversies Conversie naar “kleinere” waarde is gevaarlijk Conversie naar “grotere” waarde kan altijd double d; int n; d = n; int n; char c; n = c; Control x; Button b; x = b; Conversie naar “kleinere” waarde is gevaarlijk n = (int) d; c = (char) n; b = (Button) x;
LetterTeller class LetterTeller : Form TextBox invoer Label uitvoer StaafDiagram diagram class StaafDiagram : UserControl class TurfTab
Letterteller hoofdklasse class LetterTeller : Form { TextBox invoer; Label uitvoer; StaafDiag diagram; LetterTeller() { invoer = new TextBox(); invoer.MultiLine = true; uitvoer = new Label(); diagram = new StaafDiag(); } invoer . TextChanged += this.Bereken; void Bereken(object o, EventArgs ea) { } TurfTab tabel = new TurfTab(); tabel.Turf ( invoer.Text ); uitvoer.Text = tabel.ToString() ; diagram.Waardes = tabel.Waardes ; }
De klasse TurfTab klasse-ontwerp: wat is ... & wat kan ... & hoe? public class TurfTab { private int [ ] tellers; private int totaal; public TurfTab ( ) { ... } public void Turf (string s) { ... } override public string ToString ( ) { ... } private void turf (char c) { ... } public int Totaal { ... } public int[] Waardes { ... } }
De klasse TurfTab public class TurfTab { private int [ ] tellers; private int totaal; public TurfTab ( ) { } tellers = new int [26]; public void Turf (string s) { } int t; for (t=0; t<s.Length; t++) this.turf ( s[t] ); }
De klasse TurfTab public class TurfTab { private int [ ] tellers; private int totaal; private void turf (char c) { } if (c>='A' && c<='Z') { } tellers [ ] ++; totaal++; c - 'A' if (c>='a' && c<='z') { tellers [ c - 'a' ] ++; totaal++; } }
De klasse TurfTab public class TurfTab { private int [ ] tellers; private int totaal; override public string ToString( ) { } string result; int t; result = ""; for (t=0; t<26; t++) result += (char) t + ":" + tellers[t] + "keer\n" ; ( + 'A') result += "totaal:" + totaal; return result; }
De klasse TurfTab public class TurfTab { private int [ ] tellers; private int totaal; een eigen property! public int Totaal { get { } "mini- methodes" "mini- methodes" return totaal; set { } totaal = value; } }
geen set-minimethode: De klasse TurfTab public class TurfTab { private int [ ] tellers; private int totaal; een eigen property! public int Totaal { get { } "mini- methodes" "mini- methodes" return totaal; geen set-minimethode: read-only property set { } totaal = value; } }
De klasse TurfTab public class TurfTab { private int [ ] tellers; private int totaal; public float Gemiddelde { get mag ook nog rekenwerk doen get { } return (float)totaal / tellers.Length; } public int[] Waardes { get { } return tellers.Clone(); geef een kopie van de private array } }
De klasse StaafDiag public class StaafDiag : UserControl { private int[] waardes; alleen set-minimethode: write-only property public StaafDiag() { this.Paint += this.teken; } public int[] Waardes { } set { } this.waardes = value; this.Invalidate(); wie de property verandert, forceert een Paint private void teken(object o, PEA pea) { } // ...FillRectangle...waardes... }
De klasse StaafDiag public class StaafDiag : UserControl { private int[] waardes; private void teken(object o, PEA pea) { int max= Bieb.Grootste(max); if (max<10) max = 10; float balkH = this.Height / waardes.Length; float balkU = this.Width / max; for (int t=0; t<waardes.Length; t++) pea.Graphics.FillRectangle( Brushes.Blue, 0, t * balkH , balkU * this.waardes[t] , balkH-1 ); } }
member void type naam methode ( parameters ) blok
member void type naam methode operator op ( parameters ) blok
member void type naam methode op ( parameters ) naam ( parameters ) operator op ( parameters ) naam ( parameters ) constructor blok
member const = initialisatie veld type naam ; , void type naam methode operator op ( parameters ) naam ( parameters ) constructor blok
member const = initialisatie veld type naam ; , type naam { blok } get blok } property set void type naam methode operator op ( parameters ) naam ( parameters ) constructor blok
member const = initialisatie veld type naam ; , type naam { blok } get blok } property set indexer type this [ parameters ] void type naam methode operator op ( parameters ) naam ( parameters ) constructor blok
Voorbeeld: Simulatie van bewegende deeltjes Simulatie - object Ruimte - objecten Deeltje - objecten Button - objecten
zich zelfstandig ontwikkelende lijn van gebeurtenissen Animatie Animatie: “tekenfilm” programma toont automatisch veranderende beelden Gemakkelijk te programmeren met gebruik van de klasse “draadje” Thread zich zelfstandig ontwikkelende lijn van gebeurtenissen
en keert dan direct terug Maak een animatie Thread animatie; animatie = new Thread ( this.run ); animatie . Start ( ); this . run ( ); roept de methode aan die bij constructor is meegegeven en keert dan direct terug (terwijl de methode nog bezig is)
De methode run class Simulatie : Form { oneindige herhaling! } oneindige herhaling! void run ( ) { while (true) { } this . stap_Click (this, null ); Thread . Sleep (50); milliseconden }
Starten van de animatie class Simulatie : Form { } Thread animatie; bool beweegt; void auto_Click(object o, EventArgs ea ) { if (beweegt) { auto.Text = "Start"; beweegt = false; } else { animatie = new Thread( this.run ); animatie . Start ( ); auto.Text = "Stop"; beweegt = true; }