Algoriter och Datastrukturer (ALDA/ID005) Algoritmer och datastrukturer, varför det? Algoritmer är oberoende av programmeringsspråket som används Rätt datastruktur kan vara halva lösningen på ett problem Algoritmer kommer att bli viktigare och viktigare Föreläsning 1 Introduktion till kursen, generics, design patterns Beatrice Åkerblom beatrice@dsv.su.se Henrik Bergström henrikbe@dsv.su.se 2 Datastrukturer http://www.nist.gov/dads/ Kursupplägg 3
Information för kursen Daisy Kursbeskrivning Kursmål Betygskriterier Schema Kursresultat Kurs-PM Länkar till föreläsningsbilder Instruktioner för inlämningsuppgifter Kursbok Data Structures and Algorithm Analysis in Java av Mark Allen Weiss 5 6 Hederskodex Inlämningsuppgifterna skall lösas och redovisas individuellt. Attlåta någon annan lösa en inlämningsuppgift och sedan lämna in den kan leda till avstängning från studierna. Trots att varje student skall skriva sin kod själv är det dock tillåtet att diskutera med andra(studenter/lärare/syskon/etc.) och få hjälp med vissa bitar. Om man på detta sätt får hjälp med en del av sitt program måste manändå veta helt vad den delen gör och man måste skriva i en kommentar till koden att man har fått hjälp och av vem. Läs mer om detta på: http://www.dsv.su.se/utbildning/hederskodex Aktiviteter Föreläsning Grupparbete (2-3 personer) Seminarium individuell övning och gruppövning Individuella uppgifter muntlig redovisning 7 8
Vad är Generics? Generics Generics är abstraktioner som bygger på typer Klasser, gränssnitt och metoder kan parametriseras m.h.a.typer Generics möjliggör ökad läsbarhet och typsäkerhet 10 Förr i tiden Nuförtiden Java 1.0 1.4 hade inte stöd för generics Många ansåg att detta var Javas största svaghet Inga homogena samlingsklasser Stort behov av typomvandlingar Inga kontroller vid kompilering ledde till att fel upptäcktes sent LinkedList list = new LinkedList(); list.add(new Integer(0)); Integer i = (Integer) list.get(0); String s = (String) list.get(0); //ger fel vid //körning Samlingsklasser är homogena Minskat behov av typomvandlingar Kontroller vid kompilering baserad på statisk typinformation LinkedList<Integer> list = new LinkedList<Integer>(); list.add(new Integer(0)); Integer i = list.get(0); String s = list.get(0); // ger fel vid kompilering 11 12
class Stack { void push(object o) { Object pop() { String s = "Hello"; Stack st = new Stack (); st.push(s); s = (String) st.pop(); class Stack<A> { void push(a a) { A pop() { String s = "Hello"; Stack<String> st = new Stack<String>(); st.push(s); s = st.pop(); Generics och arv Begränsningar kan definieras för vilken typ av typer som får användas som typ-parametrar till en klass Detta kan åstadkommas genom att ange en godkänd gemensam supertyp för de typ-parametrar som kan användas Subtyper skapas i Java med hjälp av arv 13 14 Begränsning av typ-parameter Begränsning av typ-parameter, forts. interface Comparable<I> { boolean lessthan(i); Inuti en typ-parametriserad klass kan typ-parametern användas som vilken typ somhelst class PriorityQueue<T extends Comparable<T>> { T queue[ ] ; void insert(t t) { if ( t.lessthan(queue[i]) ) T remove() { 15 public class OuterClass<T> { private class InnerClass<E extends T> { 16
Begränsning av typ-parameter, forts. Generics och subtypning Flera begränsningar kan användas för att specificera en typ-parameter: Kan vi se några problem med följande kodsnutt? <T extends A & B & C & > List<String> ls = new ArrayList<String>(); //1 List<Object> lo = ls; //2! interface A {! interface B { Rad 1 innebär inga problem. På rad 2 måste vi dock fråga oss om en lista av String är en lista av Object?! class MultiBounds<T extends A & B> {!! 17 o.add(new Object()); // 3 För alla typer A och B, gäller att Subtype(A, B)!=> Subtype (Collection<A>, Collection<B>) 18 Subklassning Hantera alla samlingar import java.awt.color; public class Subclass extends MyClass<Color> { På den gamla tiden före Java 1.5 skulle man kunna göra på följande sätt för att skriva ut alla element från alla typer av samlingar: // You almost always need to supply a constructor public Subclass(Color color) { super(color); public static void main(string[ ] args) { Subclass sc = new Subclass(Color.GREEN); sc.print(color.white); 19 void printcollection(collection c) {! Iterator i = c.iterator();! for (k = 0; k < c.size(); k++) {!! System.out.println(i.next()); 20
Hantera alla samlingar, ett första försök Nytt försök med wildcards void printcollection(collection<object> c) {! for (Object e : c) {!! System.out.println(e);! Mycket mindre användbar Den gamla kunde användas på alla typer av samlingar med alla typer av typ-parametrar Collection<Object> är ju inte en supertyp för alla typer av samlingar 21 Vad är supertypen för alla typer av samlingar med alla typer av typparametrar? Svaret är att det är samlingen av okänd typ, dvs Collection<?> Det ger oss en samling vars elementtyp kan vara vilken somhelst void printcollection(collection<?> c) {! for (Object e : c) {!! System.out.println(e);! 22 Design patterns Designmönster Vad är det? Ska ni veta Var hittar man dem? 24
Professor Coupling Sheep class Sheep { public Sheep( ) { //this is a spanish sheep, so it sounds like a spanish sheep! System.out.println( "beeeee. I'm a new Sheep" ); 25 26 Cloning machine Cow class CloningMachine { public CloningMachine( ) {! public Sheep buildclone( ) { return new Sheep( );! public Sheep[] buildmanyclones( int clonenum ) { Sheep[] returnarray = new Sheep[ clonenum ];!! for( int k=0; k< clonesnum; k++ ) { returnarray[ k ] = new Sheep( );!!!!! return returnarray;!! 27 28
Cloning machine Cloning machine class CloningMachine { function CloningMachine( ) {! public Sheep buildclone( ) { return new Sheep( ); public Cow buildcowclone( ) { return new Cow( );! public Sheep[] buildmanyclones( int clonenum ) { Sheep[] returnarray = new Sheep[ clonenum ];!! for( int k=0; k< clonesnum; k++ ) { returnarray[ k ] = new Sheep( );!!!!! return returnarray;!! 29 class CloningMachine{ public CloningMachine( ){! public Object buildclone( String type ) { if( type.equals( "sheep" ) ) { return new Sheep( ); else if ( type.equals( "cow" ) ) { return new Cow( );! public Sheep[] buildmanyclones( int clonenum ) { Sheep[] returnarray = new Sheep[ clonenum ];!! for( int k=0; k< clonesnum; k++ ) { returnarray[ k ] = new Sheep( );!!! return returnarray;!! 30 CloneableAnimal public interface CloneableAnimal extends Cloneable { public CloneableAnimal duplicate( ); Sheep public class Sheep implements CloneableAnimal { public Sheep( ) { System.out.println( "Sheep template created" ); public CloneableAnimal duplicate( ) { System.out.println( "the Sheep will clone itself" ); Sheep returnvalue = null; try { returnvalue = ( Sheep ) super.clone( ); catch( Exception e ) { System.out.println( "error cloning Sheep" ); return returnvalue; 31 public String tostring( ) { return "I'm a sheep clone, beeeeee"; 32
A Cow public class Cow implements CloneableAnimal { public Cow( ) { System.out.println( "Cow template created" ); public CloneableAnimal duplicate( ) { System.out.println( "creating a new Cow instance" ); return new Cow( ); public String tostring( ) { return "Muuuu, cow clone" ; Cloning machine public class CloningMachine { public CloningMachine( ) { public CloneableAnimal newclone( CloneableAnimal template ) { return template.duplicate( ); public CloneableAnimal[] clonemany( int itemcount, CloneableAnimal template ) { CloneableAnimal[] returnvalue = new CloneableAnimal[itemCount]; for( int i=0; i< itemcount; i++ ) { returnvalue[ i ] = template.duplicate( ); return returnvalue; 33 34 public class ProfessorCoupling { public static void sayit( String words ){ System.out.println( "" ); System.out.println( words ); System.out.println( "" ); public static void main( String[] args ){ CloningMachine cm = new CloningMachine(); sayit( "creating Sheep and Cow templates" ); Sheep sheeptemplate = new Sheep( ); Cow cowtemplate!! = new Cow( ); Cow clonedcow = (Cow) cm.newclone(cowtemplate); sayit( "first cloned cow" ); Sheep clonedsheep = (Sheep) cm.newclone(sheeptemplate); sayit( "first cloned sheep" ); System.out.println( clonedsheep ); sayit( "Creating 10 new cows" ); CloneableAnimal[] newcows = cmachine.clonemany( 10, cowtemplate ); That Was the Prototype pattern sayit( "Creating 10 new Sheeps" ); CloneableAnimal[] newsheeps = cmachine.clonemany( 10, sheeptemplate ); sayit( "Testing the cows created" ); for( int i=0; i< newcows.length; i++ ) { System.out.println( newcows[ i ] ); sayit( "Testing the sheeps created" ); for( int i=0; i< newsheeps.length; i++ ) { System.out.println( newsheeps[ i ] ); 36
Different roles cow sheep??? soldier cow peasant cow soldier sheep peasant sheep soldier??? peasant??? 37 Interfaces All classes implement: public interface ISubject { public Role getextension( String extname ); Extension Objects pattern Interface to encapsulate actions: 39 public interface IBasicActions { public void movearms( ); public void movelegs( ); public void eat( ); 40
Sheep Roles public class Sheep implements ISubject, IBasicActions { private SoldierRole soldierrole; private PeasantRole peasantrole; public Sheep( ) { System.out.println( "I'm a sheep" ); public Role getextension( String extname ){ Role returnvalue = null; if( extname.equals( "SoldierRole" ) ) { if( soldierrole == null ) { returnvalue = new SoldierRole( this ); else { returnvalue = soldierrole; if( extname.equals( "PeasantRole" ) ) { if( peasantrole == null ) { returnvalue = new PeasantRole( this ); else { returnvalue = peasantrole; return returnvalue; 41 public abstract class Role { public class SoldierRole extends Role implements ISoldierActions { private IBasicActions subject; public SoldierRole( IBasicActions subject ) { this.subject = subject; System.out.println( "SoliderBehaviour created" ); public void destroy( ) { public void moveto( ) { 42 Refactored Sheep public class ProfessorCoupling { public static void main( String[ ] args ) { Sheep sheep = new Sheep( ); ISoldierActions soldiersheep = (ISoldierActions) sheep.getextension("soldierrole"); soldiersheep.destroy( ); IPeasantActions peasantsheep = (IPeasantActions) sheep.getextension("peasantrole"); peasantsheep.dogardening( ); public interface ISubject { public Role getextension( String extname ); public void addextension( String extname, Role extension ); public void removeextension( String extname ); import java.util.hashmap; public class Sheep implements ISubject, IBasicActions { private HashMap rolescol; public Sheep( ) { System.out.println( "I'm a sheep" ); rolescol = new HashMap( ); public Role getextension( String extname ) { return ( Role ) rolescol.get( extname ); public void addextension( String extname, Role extension ) { rolescol.put( extname, extension ); public void removeextension( String extname ) { rolescol.remove( extname ); public void movearms( ) { // movement implementation System.out.println( "the sheep moves one arm" ); public void movelegs( ) { // movement implementation System.out.println( "the sheep moves one leg" ); public void eat( ) { // implements the way sheeps eat System.out.println( "munch. munch" ); 44
Sheep, cont d public class ProfessorCoupling { public static void main( String[ ] args ) { Sheep sheep = new Sheep( ); sheep.addextension( "SoldierRole", new SoldierRole( sheep ) ); ISoldierActions soldiersheep = ( ISoldierActions ) sheep.getextension( "SoldierRole" ); soldiersheep.destroy(); sheep.removeextension( "SoldierRole" ); sheep.addextension( "PeasantRole", new PeasantRole( sheep ) ); IPeasantActions peasantsheep = ( IPeasantActions ) sheep.getextension( "PeasantRole" ); peasantsheep.dogardening( ); public void movearms( ) { // movement implementation System.out.println( "the sheep moves one arm" ); public void movelegs( ) { // movement implementation System.out.println( "the sheep moves one leg" ); public void eat( ) { // implements the way sheeps eat System.out.println( "munch. munch" ); 46 Roles public abstract class Role { public class SoldierRole extends Role implements ISoldierActions { private IBasicActions subject; public SoldierRole( IBasicActions subject ) { this.subject = subject; System.out.println( "SoliderBehaviour created" ); public void destroy( ) { System.out.println( "Soldier interface. destroy" ); //Use some of the animal's methods subject.eat( ); public void moveto( ) { System.out.println( "Soldier Interface. moveto" ); //Use some of the animal's methods subject.movelegs( ); 47 Roles, cont d public class PeasantRole extends Role implements IPeasantActions { private IBasicActions subject; public PeasantRole( IBasicActions subject ) { this.subject = subject; System.out.println( "PeasantBehaviour created" ); public void driveto( ) { System.out.println( "I drive to " ); //Use some of the animal's methods subject.movearms( ); subject.movelegs( ); public void dogardening( ) { System.out.println( "OK, gardening" ); //Use some of the animal's methods subject.movearms( ); 48
public class SoldierRole extends Role implements ISoldierActions { private IBasicActions subject; public SoldierRole( IBasicActions subject ) { this.subject = subject; System.out.println( "SoliderBehaviour created" ); public void destroy( ) { System.out.println( "Soldier interface. destroy" ); //Use some of the animal's methods subject.eat( ); public void moveto( ) { System.out.println( "Soldier Interface. moveto" ); //Use some of the animal's methods subject.movelegs( ); public void waitformoreorders( ) { System.out.println( "I'll wait for more orders. Beeeeeee" ); class ProfessorCoupling { public ProfessorCoupling( ) { public void attack( ISoldierActions[] soldiers, IPeasantActions[] peasants ) { int soldierscount = soldiers.length; int peasantscount = peasants.length; for( int idx=0; idx< soldierscount / 2; idx++ ) { soldiers[ idx ].destroy( ); for( int idx=soldierscount/2; idx< soldierscount; idx++ ) { soldiers[ idx ].waitformoreorders( ); for( int idx=0; idx< peasantscount / 2; idx++ ) { peasants[ idx ].dogardening( ); for( int idx=peasantscount/2; idx< peasantscount; idx++ ) { peasants[ idx ].driveto( ); Read more Command Pattern Observer pattern Slut för idag! http://www.design-nation.net/en/design_patterns/ 51 52