javakurs für fortgeschrittene - uni-muenchen.de...junit 4) integraler bestandteil der java...

1

Upload: others

Post on 15-Jul-2020

1 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Javakurs für Fortgeschrittene

Einheit 11: Java 8 & JUnit

Lorenz Schauer

Lehrstuhl für Mobile und Verteilte Systeme

Page 2: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Heutige Agenda

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 2

Lernziele Sehen, was Java 8 Neues bringt Funktionale Sprachelemente und Streams kennenlernen Kurze praktische Einführung in Tests mit dem JUnit Framework

Neurungen in Java 8

Motivation

Lambda-Ausdrücke

Default-Methoden

Streams

Praxis:

Arbeiten mit Streams und Lambda

JUnit Tests

Einführung in Tests mit JUnit

Motivation

Syntax

JUnit-Tests unter Eclipse

Page 3: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Geschichtliches:

Seit Java 5 Diskussionen um Spracherweiterung für funktionaleProgrammierung: „Closure-Debatte“

Seit 2009: Notwendigkeit für Lambda-ähnliche Konstrukte

Standard in anderen Programmiersprachen

Einfache Unterstützung für Parallelisierung gesucht

Aus Closures entwickelten sich:

Lambda-Ausdrücke

Methoden- und Konstruktorreferenzen

Fester Bestandteil seit Java 8

Motivation

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 3

Page 4: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Lambda-Ausdrücke

Wir erinnern uns (letzte Stunde):

Ein Objekt, welches Iterable implementiert kann das Ziel einer for-each-Schleife sein.

Alle Collection-Klassen implementieren Iterable und damit kann eine for-each-Schleife immer über diese Sammlungen laufen:

Nachteil: Nur sequentielle Verarbeitung der Elemente einer Collection Keine Trennung von Iteration und Verarbeitung

Keine Parallelisierung!

Daher: Erweiterung des Iterable Interfaces in Java 8 um die Methode forEach(Consumer<? super T> action)

Iterieren über die Liste und Verarbeitung der Elemente nun getrennt

Parallelisierbar

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 4

Collection<String> myList = new LinkedList<String>();… // Liste befüllenfor ( String s : myList )System.out.println( s );

Page 5: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Lambda-Ausdrücke

Dieser Code sieht dafür etwas unschön aus.

Aber: Consumer<? super T> ist ein funktionales Interfaces

Daher: Verwendung eines Lambda-Ausdrucks möglich:

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 5

// Verwendung von forEachmyList.forEach(new Consumer<String>(){

@Overridepublic void accept(String arg0) {

System.out.println(arg0);}

});

// Verwendung von Lambda-Expression:myList.forEach((String element) -> System.out.println(element) );

// Oder auch:myList.forEach((element) -> System.out.println(element) );

// Oder auch:myList.forEach(element -> System.out.println(element) );

// Oder auch:myList.forEach(System.out::println);

Page 6: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Lambda-Ausdrücke: Syntax

Allgemeine Syntax: (Argumentenliste) -> Body

Bsp 1: (int x, int y) -> x+y

Bsp 2: (e) -> {System.out.println(e);}

Der Body kann: Ein einfacher Ausdruck sein

Wertet die Argumente aus der Argumentenliste nach dem Ausdruck aus und gibt das Ergebnis zurück

Oder ein ganzer {Block} sein

Block wird wie eine Methode ausgewertet -> Rückgabe über return Statement

Passt zu jedem Funktionsinterface, dessen einzige Methode die passende Parameterliste und den passenden Ergebnistyp verlangt.

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 6

// Beispiele: () -> 15 // Keine Parameter, Rückgabe: int

(int a) -> a + a // Parameter: 1 int, Rückgabe: int

(s) -> System.out.println(s) // Typ implizit! //Eingabe und Rückgabe: String

(e) -> System.out.println("Click") // Typ implizit!

Page 7: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Bekannte Beispiele

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 7

// Früher:

Runnable r = new Runnable() {

@Overridepublic void run() {

System.out.println("Hallo");}

};new Thread(r).start();

// Jetzt:

Runnable r = () -> System.out.println("Hallo");

new Thread(r).start();

// Früher:

testButton.addActionListener(new ActionListener(){@Override public void actionPerformed(ActionEvent e){

System.out.println("Click");}

});

// Jetzt:

testButton.addActionListener(e -> System.out.println("Click"));

Lambdas für Runnable

Lambdas für ActionEvents

Page 8: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Methoden-Referenzen

Methoden-Referenzen referenzieren Methoden ohne sie dabei aufzurufen.

Allg. Syntax: Receiver::Methodennamen

Wichtig dabei ist wieder: Parametertypen und Return-Typen müssen übereinstimmen und aus dem Kontext ersichtlich sein!

Es gibt folgende Methodenreferenzen:

Statische Methode: Klassenname::Methodenname

Instanzmethode: objektName::Methodenname

Bestimmter Typ: Typ::Methodenname

Konstruktor: Klassenname::new

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 8

// Beispiele:

Person::compareByAge // Statische Methodenreferenz

myObject::doSomething // Referenz auf eine Instanzmethode

String::compareToIgnoreCase // Referenz auf eine String-Methode

HashSet::new // Referenz auf einen Konstruktor

Page 9: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Noch mehr Beispiele

// Beispiel 1:ArrayList<String> myList = new

ArrayList<String>(Arrays.asList("element1","element2","element3"));

// Druchlaufen mit foreach und Lambda:myList.forEach(element -> System.out.println(element) );

// Durchlaufen mit foreach und einer Methodenreferenz:myList.forEach(System.out::println);

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 9

// Beispiel 2:

public class Programm {

public void doSomething(){

System.out.println("Hallo");System.out.println("Und noch mehr");

}public static void main(String[] args) {

Programm p = new Programm();Runnable r = p::doSomething;r.run();

}}

Page 10: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Default-Methoden

Wdh Folie 4: Erweiterung des Iterable Interfaces in Java 8 um die Methode forEach(Consumer<? super T> action)

Eine Implementierende Klasse muss alle Methoden eines Interfaces implementieren!

Was bedeutet das nun für älteren Code, wo es forEach noch nicht gab?

Einführung von Default-Methoden in Java 8!

Stellen eine Default-Implementierung der Methode bereit

Kann überschrieben werden, muss aber nicht!

Außer: Eine Klasse implementiert 2 Interfaces mit gleicher Default-Methode

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 10

// Beispiel: forEach im Interface Iterbale

default void forEach(Consumer<? super T> action) {Objects.requireNonNull(action);for (T t : this) {

action.accept(t);}

} // Realisiert im Prinzip das Durchlaufen einer Collection // Die accept-Methode des Interfaces Consumer muss spezifiziert werden.

Page 11: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Auch das Collection Framework bekommt in seinem Interface Collection<T>neue (Default)-Methoden:

default Stream<E> parallelStream()

default Stream<E> stream()

default Spliterator<E> spliterator()

Wir wollen uns im Folgenden diese Streams genauer anschauen…

Streams hatten wir bereits in der 1. Kursstunde

Sie stellen Folgen von Werten dar

Bsp.: Inputstream, Outputstream, …

Wir können aber auch Streams nutzen, um Elemente in einer Art Pipeline zu aggregieren, transformieren oder zu filtern.

Vorteil: Parallelisierbarkeit!

Default-Methoden und Collections

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 11

Page 12: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Stream<T> extends BaseStream in java.util definiert gängige Methoden für Streams:

anyMatch, count, empty, max, min, map, filter, findAny …

Streams selbst sind keine Datenstruktur, sondern definieren die Operationen, die auf Datensequenzen angewendet werden sollen

I.d.R. 3 Phasen:

Erzeugung

Bsp.: myCollection.stream()

Transformation

Bsp.: myCollection.stream().filter(…)

Aggregation

Bsp.: myCollection.stream().filter(…).forEach(…)

Streams

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 12

Page 13: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Lambdas und Streams

Dieser Code wäre wieder sehr unschön.

Hier helfen uns wieder die Lambda-Ausdrücke für eine besser Lesbarkeit und kürzerem Code:

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 13

// Beispiel:Collection<String>myList = Arrays.asList("Hello","Java");long countLongStrings = myList.stream() // Erzeugung

.filter(new Predicate<String>() { // Transformation@Overridepublic boolean test(String element) {

return element.length() > 4;}

}).count(); // Aggregation

Collection<String> myList = Arrays.asList("Hello","Java");long countLongStrings =

myList.stream() // Erzeugung.filter(element -> element.length() > 4) // Transformation.count(); // Aggregation

Page 14: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Stream Operationen

Streams erzeugen:

Entweder über das Collectioninterface

stream() bzw. parallelStream()

Oder mittels Generatoren:

IntStream.rangeClosed(5, 50)

Stream.of(4,6,10,34,100)

Stream.iterate(0, n -> n + 30)

Aus Dateien:

Files.lines(Paths.get("myFile.txt"), Charset.defaultCharset());

Stream.filter() stellt eine sog. intermediate operation dar:

D.h.: Die Eingabe wird bearbeitet und als modifizierter Stream zurückgegeben (Transformation) Weitere intermediate operations:

map, sorted, unsorted, distinct, limit, peek, …

Stream.count() ist eine sog. terminal operation:

D.h.: Die Operation steht am Ende der Pipeline und gibt das Ergebnis zurück (Aggregation) Weitere terminal operations (nicht alle für Streams definiert):

sum, min, max, reduce, findFirst, …27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 14

Page 15: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Beispiele

List<Integer> myIntList = new LinkedList<Integer>(Arrays.asList(1,3,6,8,9,23,5,2,56,54,24,7,53,253));

long listCount = myIntList.stream().count();

myIntList.stream().filter(x-> x%2 == 0).forEach(System.out::println);

myIntList.stream().filter(x-> x%2 == 0).map(x -> x * x).forEach(System.out::println);

myIntList.stream().filter(x-> x%2 == 0).map(x -> x * x).sorted().limit(4).forEach(System.out::println);

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 15

14

6 8 2 56 54 24

36 64 4 3136 2916 576

4 36 64 576

Page 16: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Schreiben Sie ein einfaches Programm, welches zunächst eine Liste (Bsp.: Array-List, LinkedList, o.Ä.) erzeugt und diese mit 100 Integer-Zufallszahlen füllt.

Erzeugen Sie einen Stream auf dieser Liste und implementieren Sie dann die folgenden Anfragen:

Lassen Sie sich alle Zahlen geordnet ausgeben (absteigend und aufsteigend)

Lassen Sie sich alle ungeraden Zahlen ausgeben!

Wie viele Zahlen befinden sich in Ihrer Liste, die durch 4 teilbar sind?

Welche ist die größte bzw. kleinste Zahl in Ihrer Liste?

Berechnen Sie die Quadratsumme der Zahlen und geben Sie das Ergebnis aus

Berechnen Sie den Durchschnitt der Zahlen und geben Sie das Ergebnis aus

Addieren Sie auf jede Zahl zunächst eine 5 und lassen Sie sich die Elemente ausgeben, die größer sind als 100

Aufgabe zu Streams und Lambdas

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 16

Page 17: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Einführung in JUnit-Tests

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 17

Page 18: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

JUnit ist:

ein Testframework zum Testen von Java-Code (Bsp.: JUnit 4)

integraler Bestandteil der Java Developement Tools von Eclipse

geeignet für automatisiertes Testen von Modulen

Extreme Programming (test-driven software development)

Zuerst die Tests, dann der Code

Aber auch zum testen von bestehendem Code

Trennung von Test- und Programmcode:

Testklasse

Enthält Methoden zum Testen von Code

Testmethode

@Test Methode (public, void)

Testfall

Vorgehensweise (Input -> erw. Output)

Motivation & Eigenschaften

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 18

Page 19: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Verwendung & Syntax

Neue Testklasse erstellen:

New -> JUnit Test Case

Namen wählen

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 19

// Beispiel einer einfachen Testklasse:

import static org.junit.Assert.*;import org.junit.Test;

public class TestFeatures {

@Testpublic void testMyFeature() {

fail("Not yet implemented");}

}

Statischer importAlle statischen Methoden der Klasse Assert sind lokal verfügbar

Import von TestFür Annotations

Testmethode

Assert-Methode Test schlägt fehl.

Page 20: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Neben @Test existieren weitere wichtige Annotationen:

Weitere Annotationen

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 20

Annotation Erläuterung

@Test (expected = … Exception.class) Test ist nur erfolgreich, wenn die entspr. Exception geworfen wird.

@Test (timeout = … ms) Test ist nur erfolgreich, wenn die entspr. Zeit nicht überschritten wird.

@Before Wird immer vor den Tests ausgeführt. Dient für einen kontrollierten Start-Zustand

@After Wird immer nach jedem Test ausgeführt. Dient für einen sauberen Abschluss (Aufräumarbeiten)

@BeforeClass Methode muss statisch sein. Wird einmal vor dem Aufruf aller Testmethoden ausgeführt

@AfterClass Methode muss statisch sein. Wird einmal nach dem Aufruf aller Testmethoden ausgeführt

Page 21: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Neben fail() existieren weitere wichtige Assert-Methoden:

Weitere Assert-Methoden

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 21

Assert-Methode Erläuterung

assertEquals(Object exp, Object act) Prüft auf identische Objekte

assertFalse(boolean condition) Prüft, ob Bedingung false(Gegenstück: assertTrue)

assertNotNull(Object object) Prüft, ob Objekt instanziiert wurde. (Gegenstück: assertNull)

assertNotSame(Object unexp, Object act) Prüft, ob zwei Referenzen auf unterschiedliche Objekte verweisen. (Gegenstück: assertSame)

fail(String message) Lässt einen Test fehlschlagen und gibt die Meldung message aus.

Page 22: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Beispiel

public class Programm { // Programm-Code

private Collection<String> myCollection;

public Programm(){myCollection = new ArrayList<>(Arrays.asList("Peter","Uwe"));

}

public Collection<String> getMyCollection(){return this.myCollection;

}

public static void main(String[] args) {// TODO Auto-generated method stub

}}

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 22

public class TestList { //Test-Code

private Programm p;

@Beforepublic void init(){

this.p = new Programm();}

@Testpublic void testMyCollection() {

Collection<String> myList = p.getMyCollection();int result = myList.size();assertEquals(2, result);

}}

Page 23: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Nehmen Sie einen fertigen Code (Bspw.: blackjack von letzter Stunde) und implementieren Sie hierfür eigene Testmethoden mithilfe von JUnit 4.

Als Beispiel für den Blackjack-Code könnten Sie bspw. überprüfen,

ob ein Spieler auch eine Karte erhält, wenn er eine zieht.

ob ein Spieler zu Beginn keine Karte hat.

ob die Spieler nacheinander ziehen

ob ein Spieler wirklich aufhört, wenn er über 17 Punkte erreicht hat.

ob der Dealer die Karten auch mischt

usw.

Aufgabe zu JUnit Tests

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 23

Page 24: Javakurs für Fortgeschrittene - uni-muenchen.de...JUnit 4) integraler Bestandteil der Java Developement Tools von Eclipse geeignet für automatisiertes Testen von Modulen Extreme

Vielen Dank!!!

fürs Kommen

Zuhören

Mitmachen

Vielen Dank!

27.07.2017 Javakurs 11: Java 8 & JUnit - Lorenz Schauer 24