{"id":1030,"date":"2015-10-26T14:09:06","date_gmt":"2015-10-26T14:09:06","guid":{"rendered":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/?p=1030"},"modified":"2020-06-17T10:33:15","modified_gmt":"2020-06-17T10:33:15","slug":"ducktyping-und-java-8-methodenreferenzen","status":"publish","type":"post","link":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/","title":{"rendered":"Ducktyping &#038; Java 8 Methodenreferenzen"},"content":{"rendered":"\n<p>Einige Programmiersprachen bieten ein Feature mit dem etwas eigenartigen Namen \u201cDucktyping\u201d. Java z\u00e4hlt leider nicht dazu. In diesem Artikel m\u00f6chte ich kurz erkl\u00e4ren, was Ducktyping ist und wie man mit den in Java 8 eingef\u00fchrten Methodenreferenzen zumindest einen \u00e4hnlichen Effekt erzielen kann.<\/p>\n\n\n\n<p>Am bekanntesten ist das Konzept von Ducktyping vermutlich aus JavaScript. Der Begriff \u201cDucktyping\u201d geht wohl auf ein Gedicht des amerikanischen Schriftstellers <a href=\"https:\/\/de.wikipedia.org\/wiki\/James_Whitcomb_Riley\">James Whitcomb Riley<\/a> zur\u00fcck, worin es hei\u00dft:<\/p>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\"><p>\u201cWhen I see a bird that walks like a duck and swims like a duck and quacks like a duck, I call that bird a duck.\u201d<br>\u201cWenn ich einen Vogel sehe, der l\u00e4uft wie eine Ente und schwimmt wie eine Ente und schnattert wie eine Ente, dann nenne ich diesen Vogel auch Ente.\u201d<\/p><\/blockquote>\n\n\n\n<p>Wie passt das mit Programmierung zusammen? Stellen wir uns vor wir haben eine Funktion, die ein Enten-Objekt als Parameter erwartet. In der Funktion wollen wir die \u201cschnattern\u201d-Methode der Ente aufrufen. Ob es sich bei dem \u00fcbergebenen Objekt aber wirklich um eine Ente handelt, kann uns in vielen F\u00e4llen eigentlich herzlich egal sein \u2013 Hauptsache es besitzt eine Methode \u201cschnattern\u201d mit der passenden Signatur. Bei Ducktyping wird also die Frage \u201cIst es eine Ente?\u201d nicht am tats\u00e4chlichen Typ des Objekts festgemacht, sondern an den Eigenschaften, die das Objekt besitzt.<\/p>\n\n\n\n<p>Ein anderes, realeres Beispiel ist die <a href=\"https:\/\/api.jquery.com\/jquery.ajax\/#jQuery-ajax-settings\">AJAX-Funktion von JQuery<\/a>. Diese erwartet als Argument ein Objekt, welches einen url-Wert und einen success-Callback enth\u00e4lt (Stark vereinfacht. Tats\u00e4chlich gibt es noch zahlreiche weitere Varianten bei JQuery).<\/p>\n\n\n\n<p>Java unterst\u00fctzt kein Ducktyping. In der Methodensignatur muss f\u00fcr jedes Argument der richtige Typ angegeben werden. Ein Argument muss also beispielsweise das \u201cEnte\u201d-Interface implementieren. Es reicht nicht, dass eine Klasse die gleichen Methoden besitzt, die im Interface vorgesehen sind, nein es muss auch wirklich&nbsp;implements Ente geschrieben werden. Folgendes Beispiel, in Anlehnung an das JQuery-AJAX-Beispiel, soll das verdeutlichen:<\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<pre class=\"wp-block-code\"><code>    public interface Request {\n      String getUrl();\n      void callback(String result);\n    }\n    public class MyRequest implements Request {\n      public String getUrl() {\n        return \"http:\/\/blog.saxsys.de\";\n      }\n      public void callback(String result) {\n        System.out.println(result);\n      }\n    }\n    public void ajax(Request request) {\n      ...\n    }<\/code><\/pre>\n\n\n\n<div style=\"height:50px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<p>Ich habe ein Interface&nbsp;Request definiert und eine implementierende Klasse MyRequest. Die Methode getUrl gibt die Ziel-Adresse zur\u00fcck und die callback-Methode wird von unserem AJAX-Framework aufgerufen, sobald die Antwort eingetroffen ist. Da die ajax-Methode ein Argument vom Typ Request verlangt, kann ich ohne Probleme eine Instanz von MyRequest benutzen. Habe ich aber beispielsweise folgende Klasse, sieht die Sache ganz anders aus:<\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<pre class=\"wp-block-code\"><code>    public class OtherRequest {\n      public getUrl(){\n        return \"http:\/\/stage-sgs.dsinet.de\";\n      }\n      public void callback(String result) {\n        System.out.println(result);\n      }\n    }<\/code><\/pre>\n\n\n\n<div style=\"height:50px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<p>Obwohl diese Klasse ebenfalls die beiden ben\u00f6tigten Methoden mit der identischen Signatur besitzt, w\u00fcrde die ajax-Methode eine Instanz dieser Klasse verweigern, da die Klasse das nicht das Interface Request implementiert. Das kann oft \u00e4rgerlich sein, vor allem, wenn man eine gegebene Klasse nicht einfach selbst ver\u00e4ndern kann, also nicht einfach implements Request dran schreiben kann, beispielsweise wenn diese aus einer Drittbibliothek stammt.<\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<h2 class=\"wp-block-heading\">Ad-Hoc-Implementation von Interfaces<\/h2>\n\n\n\n<p>Bei anderen Programmiersprachen ist das zum Teil anders: Bei <a href=\"https:\/\/www.haskell.org\/\">Haskell<\/a> beispielsweise gibt es zwar keine \u201cInterfaces\u201d im Java-Sinne aber man k\u00f6nnte Haskells \u201c<a href=\"http:\/\/learnyouahaskell.com\/types-and-typeclasses\">type classes<\/a>\u201d in etwa mit Interfaces vergleichen. Und hier kann man Typen auch unabh\u00e4ngig von der Typdefinition nachtr\u00e4glich zu beliebigen <a href=\"http:\/\/learnyouahaskell.com\/making-our-own-types-and-typeclasses#typeclasses-102\">Type-Classes hinzuf\u00fcgen<\/a>. Ich k\u00f6nnte also meinen Typ OtherRequest der Type-Class Request hinzuf\u00fcgen, ohne dass ich den Quellcode von OtherRequest anfassen muss. Anschlie\u00dfend kann ich OtherRequest-Werte als Parameter f\u00fcr Funktionen nutzen, die Request als Typ verlangen.<\/p>\n\n\n\n<p>Schauen wir uns ein Beispiel an:<\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<pre class=\"wp-block-code\"><code>    class Request r where\n      getUrl :: r -> String\n    ajax :: (Request r) => r -> IO ()\n    ajax r = do print $ getUrl r<\/code><\/pre>\n\n\n\n<div style=\"height:50px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<p>Hier wird eine Type-Class&nbsp;Request mit einer Funktion getUrl definiert, die einen konkreten Request entgegen nimmt und einen String zur\u00fcck gibt. Jeder Datentyp, der dieser Type-Class hinzugef\u00fcgt wird muss also eine solche Funktion bereitstellen. Darunter befindet sich die ajax-Funktion, die einen Request entgegen nimmt und eine IO-Aktion zur\u00fcck gibt. Die hier gezeigte Implementierung ist nur ein Platzhalter und f\u00fchrt nicht wirklich einen AJAX-Request aus, sondern gibt lediglich die URL auf der Kommandozeile aus. Dazu kann es aber auf die&nbsp;getUrl Funktion zur\u00fcck greifen, da diese ja in der Type-Class definiert wurde.&nbsp; Dies entspricht also unserem AJAX-Library-Code.<\/p>\n\n\n\n<p>In unserem Programm k\u00f6nnten wir nun unseren eigenen Datentyp f\u00fcr unseren Request definieren. Um das AJAX-Framework benutzen zu k\u00f6nnen m\u00fcssen wir unseren Datentyp zur \u201cRequest\u201d-Type-Class hinzuf\u00fcgen:<\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<pre class=\"wp-block-code\"><code>    data OtherRequest = OtherRequest {url::String} deriving (Show)\n    instance Request OtherRequest where\n      getUrl = url\n    x = OtherRequest \"http:\/\/www.saxsys.de\"\n    ajax x<\/code><\/pre>\n\n\n\n<div style=\"height:50px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<p>Mit dem data-Schl\u00fcsselwort wird in Haskell ein neuer Typ definiert, der in unserem Fall \u201cOtherRequest\u201d hei\u00dft und einen String \u201curl\u201d besitzt. Haskell erzeugt damit eine Funktion \u201curl\u201d, mit der Signatur OtherRequest -&gt; String, die also ein OtherRequest-Wert entgegen nimmt und einen String zur\u00fcck gibt.<\/p>\n\n\n\n<p>Mit&nbsp;instance wird unser Typ der Type-Class hinzugef\u00fcgt. Mit der Zeile \u201cgetUrl = url\u201d sagen wir aus, dass die \u201curl\u201d-Funktion unseres Typs benutzt werden soll, wenn \u201cgetUrl\u201d von der Type-Class aufgerufen wird. Wir k\u00f6nnten an der Stelle aber auch eine andere Implementierung angeben. Dies ist also vergleichbar mit der Situation in Java, wo in einer Klasse eine Methode implementiert wird, die durch ein Interface vorgeschrieben wird.<\/p>\n\n\n\n<p>Der untere Teil des Codeausschnitts zeigt, wie wir das ganze benutzen k\u00f6nnen. Wir erstellen einen \u201cOtherRequest\u201d-Wert und weisen ihm den Namen \u201cx\u201d zu. Anschlie\u00dfend wird die \u201cajax\u201d-Funktion mit x als Argument aufgerufen. Da wir \u201cOtherRequest\u201d der Type-Class \u201cRequest\u201d hinzugef\u00fcgt haben, funktioniert dieser Aufruf wie erwartet.<\/p>\n\n\n\n<p>Da Haskell keine objektorientierte Sprache ist, l\u00e4sst sich das ganze nicht komplett mit Java vergleichen. Der springende Punkt ist aber: Die Definition unseres Typs und das Hinzuf\u00fcgen zur Type-Class (also das Implementieren des Interfaces) sind zwei unabh\u00e4ngige Vorg\u00e4nge, die an unabh\u00e4ngigen Stellen im Code durchgef\u00fchrt werden k\u00f6nnen. Der Typ \u201cOtherRequest\u201d h\u00e4tte auch aus einer Dritt-Bibliothek stammen k\u00f6nnen. Trotzdem k\u00f6nnten wir ihn f\u00fcr unser Programm der ben\u00f6tigten Type-Class hinzuf\u00fcgen um ihn benutzen zu k\u00f6nnen. In Punkto Erweiterbarkeit ist diese Variante also ein guter Ersatz f\u00fcr Ducktyping, vorallem da sogar von der konkreten Benennung abstrahiert werden kann (siehe \u201cgetUrl = url\u201d).<\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<h2 class=\"wp-block-heading\">Dynamische oder statische Typisierung<\/h2>\n\n\n\n<p>Ducktyping wird in der Regel vor allem im Zusammenhang mit dynamisch Typisierten Sprachen wie JavaScript genannt. Bei diesen wird also zur Laufzeit bestimmt, ob ein Objekt die n\u00f6tigen Methoden und Attribute besitzt. Aber auch bei statischer Typisierung ist Ducktyping m\u00f6glich. Die Pr\u00fcfung, ob ein Objekt \u201ceine Ente ist\u201d, findet dann zur Compile-Zeit statt. Ein gutes Beispiel ist <a href=\"http:\/\/www.typescriptlang.org\/\">Typescript<\/a>. Unser Request-Beispiel von vorhin k\u00f6nnte in Typescript so aussehen:<\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<pre class=\"wp-block-code\"><code>    interface Request {\n      getUrl(): string\n      callback(result: String)\n    }\n    class MyRequest implements Request {\n      getUrl() {\n        return \"http:\/\/example.org\";\n      }\n      callback(result: String) {\n        console.log(result);\n      }\n    }\n    class OtherRequest {\n      getUrl() {\n        return \"http:\/\/example.org\";\n      }\n      callback(result: String) {\n        console.log(result);\n      }\n    }\n    function ajax(request: Request) {\n    }\n    var r1 = new MyRequest();\n    var r2 = new OtherRequest();\n    ajax(r1);\n    ajax(r2);<\/code><\/pre>\n\n\n\n<div style=\"height:50px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<p>Die ajax-Funktion erwartet ein Argument vom Interface-Typ Request. Aber auch eine Instanz von OtherRequest wird vom Compiler akzeptiert, obwohl diese Klasse das Interface nicht explizit implementiert \u2013 es reicht, dass alle Methoden mit der korrekten Signatur vorhanden sind. Der Code kann <a href=\"http:\/\/www.typescriptlang.org\/Playground#src=interface%20Request%20{%0A%09getUrl%28%29%3A%20string%0A%09callback%28result%3A%20String%29%0A}%0A%0Aclass%20MyRequest%20implements%20Request%20{%0A%09getUrl%28%29%20{%0A%09%09return%20%22http%3A%2F%2Fexample.org%22%3B%0A%09}%0A%09callback%28result%3A%20String%29%20{%0A%09%09console.log%28result%29%3B%0A%09}%0A}%0A%0Aclass%20OtherRequest%20{%0A%09getUrl%28%29%20{%0A%09%09return%20%22http%3A%2F%2Fexample.org%22%3B%0A%09}%0A%09callback%28result%3A%20String%29%20{%0A%09%09console.log%28result%29%3B%0A%09}%0A}%0A%0A%0Afunction%20ajax%28request%3A%20Request%29%20{%0A%09%0A}%0A%0Avar%20r1%20%3D%20new%20MyRequest%28%29%3B%0Avar%20r2%20%3D%20new%20OtherRequest%28%29%3B%0A%0Aajax%28r1%29%3B%0Aajax%28r2%29%3B\">hier<\/a> auch live ausprobiert werden.<\/p>\n\n\n\n<p>Zur\u00fcck zu Java. Wie oben schon erw\u00e4hnt, unterst\u00fctzt Java kein Ducktyping. Mit den Methoden-Referenzen aus Java 8 kann man aber einen \u00e4hnlichen Effekt erzielen, der zwar nicht so elegant, in einigen Situationen aber trotzdem sehr n\u00fctzlich sein kann. Vor allem dann, wenn die zu benutzende Klasse eben nicht ver\u00e4ndert werden kann oder soll.<\/p>\n\n\n\n<p>Die Idee ist, einer Funktion nicht nur das Objekt mitzugeben, sondern auch mitzuteilen, wie die Funktion an die notwendigen Methoden des Objekts herankommen kann. Schauen wir uns das wieder am AJAX-Beispiel an:<\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<pre class=\"wp-block-code\"><code>    public void ajax(Request request) {\n      String url = request.getUrl();\n      ...\n      String result = ...\n      request.callback(result);\n    }\n    public &lt;T> void ajax(T request, Function&lt;T,String> urlExtractor, BiConsumer&lt;T, String> callback) {\n      String url = urlExtractor.apply(request);\n      ...\n      String result = ...;\n      callback.accept(request, result);\n    }<\/code><\/pre>\n\n\n\n<div style=\"height:50px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<p>Wer bisher noch wenig mit den Funktionalen Klassen und Interfaces von Java 8 zutun hatte, f\u00fcr den sieht die Signatur der zweiten \u00fcberladenen ajax-Methode vielleicht etwas gew\u00f6hnungsbed\u00fcrftig aus. Zun\u00e4chst definiert die Methode einen generischen Typ-Parameter T ohne dabei irgendwelche Typ-Grenzen festzulegen. Es kann folglich jede beliebige Instanz als erstes Argument \u00fcbergeben werden, solange sichergestellt ist, dass die Funktionen, die als zweites und drittes Argument \u00fcbergeben werden, zu diesem Typ passen. Das zweite Argument ist eine Funktion, die f\u00fcr ein gegebenes Objekt vom Typ T einen String (n\u00e4mlich die URL) zur\u00fcck liefert. Als drittes wird ein <em>BiConsumer<\/em> \u00fcbergeben, sprich eine Funktion, die zwei Argumente (wieder das Request-Objekt und den Ergebnis-String) entgegen nimmt und keinen R\u00fcckgabewert hat. Mit Lambdas kann diese Funktion nun so aufgerufen werden:<\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<pre class=\"wp-block-code\"><code>    MyOtherRequest myRequest = new MyOtherRequest();\n    ajax(myRequest, req -> req.getUrl(), (req, result) - req.callback(result));<\/code><\/pre>\n\n\n\n<div style=\"height:50px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<p>Besser lesbar wird es mit Methodenreferenzen:<\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<pre class=\"wp-block-code\"><code>    OtherRequest otherRequest = new OtherRequest();\n    ajax(myRequest, OtherRequest::getUrl, OtherRequest::callback);<\/code><\/pre>\n\n\n\n<div style=\"height:50px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<p>Die Zeile liest sich quasi so: Nimm dieses Request-Objekt. Um an die URL zu gelangen, rufe die getUrl-Methode auf dem Request-Objekt auf. Und zur Verarbeitung des Ergebnisses bitte die callback-Methode auf dem Objekt aufrufen. Dieses Vorgehen ist zwar kein Ducktyping.&nbsp; Aber man kann es in Situationen nutzen, in denen man sich sonst Ducktyping w\u00fcnschen w\u00fcrde. Die Methodensignatur dr\u00fcckt gewisserma\u00dfen Anforderungen an ein gegebenes Objekt aus, die von dem Objekt unterst\u00fctzt werden m\u00fcssen. Interessant dabei ist auch, dass die tats\u00e4chliche Benennung der Methoden bei dieser Variante egal ist. OtherRequest h\u00e4tte seine Callback-Methode auch \u201crufMichAn_Sofort\u201d nennen k\u00f6nnen. \u00dcbrigens h\u00e4tte man im konkreten Fall die Signatur von ajax noch anders gestalten k\u00f6nnen:<\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<pre class=\"wp-block-code\"><code>    public void ajax(Supplier&lt;String> urlSupplier, Consumer&lt;String> callback) {\n      String url = urlSupplier.get();\n      ...\n      callback.accept(\"das Result\");\n    }\n    \/\/ Aufruf\n    ajax(otherRequest::getUrl, otherRequest::callback);<\/code><\/pre>\n\n\n\n<div style=\"height:50px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<p>Hier wird direkt eine Funktion zum Beschaffen der URL und ein Funktion zum Verarbeiten des Ergebnisses \u00fcbergeben. Aus Sicht der ajax-Funktion spielt es keine Rolle, ob es da ein Request-Objekt gibt und von welchem Typ es ist. Wichtig ist der Unterschied beim Aufruf der Methode: Die Methodenreferenzen beziehen sich hier auf die Instanz otherRequest (mit kleinem Anfangsbuchstaben), w\u00e4hrend im oberen Beispiel die Methodenreferenzen auf die Klasse abzielten (OtherRequest mit gro\u00dfem Anfangsbuchstaben). Aus API-Design-Gesichtspunkten ist diese Variante am besten, da die ajax-Methode die wenigsten Annahmen \u00fcber den Aufrufer anstellt und damit sehr gut komponierbar ist. Es gibt aber Situationen, wo die oben gezeigte \u201cQuasi-Ducktyping\u201d-Variante notwendig ist und man wirklich Objekte als Parameter entgegen nehmen m\u00f6chte. Beispielsweise haben wir bei der Entwicklung des <a href=\"https:\/\/github.com\/sialcasa\/mvvmFX\/wiki\/ModelWrapper\">Model-Wrappers<\/a>, der Teil von <a href=\"https:\/\/sogehtsoftware.de\/2015\/07\/mvvmfx-model-view-viewmodel-javafx-teil-1\/\">mvvmFX<\/a> ist, diese Variante benutzt um Getter- und Setter-Methoden eines gewrappten Objekts bekannt zu machen.<\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<h2 class=\"wp-block-heading\">Fazit<\/h2>\n\n\n\n<p>Die Frage, ob Java als Sprache Ducktyping direkt unterst\u00fctzen sollte, \u00e4hnlich beispielsweise zu der oben gezeigten TypeScript-Variante, ist aber umstritten. Denn nur weil eine Klasse die gleichen Methodensignaturen besitzt ist ja noch lange nicht klar, ob es auch wirklich kompatibel oder fachlich passend ist. Mein Eindruck ist, dass viele Java-Entwickler ohnehin eher defensiv eingestellt sind, was man z.B. an der <a href=\"http:\/\/steve-yegge.blogspot.de\/2010\/07\/wikileaks-to-leak-5000-open-source-java.html\">Debatte um \u201cfinal\u201d bei Methoden und Klassen sieht<\/a>. Daher scheint es mir unwahrscheinlich, dass Java in n\u00e4chster Zukunft echtes Ducktyping bekommen wird. Auch die M\u00f6glichkeit der Ad-Hoc-Implementierung von Interfaces, \u00e4hnlich wie es oben f\u00fcr Haskell gezeigt wurde, scheint wohl nicht auf der Liste der Erweiterungen zu stehen, die in n\u00e4chster Zeit f\u00fcr die Java-Sprache zu erwarten sind.<\/p>\n\n\n\n<p>Als Fazit l\u00e4sst sich aber sagen, dass die funktionalen Interfaces von Java 8 hier zumindest einige Erleichterung bringen. Statt bestimmte eingeschr\u00e4nkte Typen f\u00fcr Methoden-Argumente vorschreiben zu m\u00fcssen, k\u00f6nnen so beliebige Argumente verwendet werden, wenn mittels Funktionen mitgeteilt wird, wie diese Argumente zu interpretieren sind. Dies erleichtert die Integration von Fremdcode und vermindert Kopplung.&nbsp; Und mittels Methodenreferenzen kann eine noch bessere fachliche Ausdrucksform, als mit puren Lambda-Ausdr\u00fccken, erreicht werden.<\/p>\n\n\n\n<p>Die wichtigste Erkenntnis ist aber wieder einmal: Es lohnt sich, einen Blick \u00fcber den&nbsp; Java-Tellerrand zu wagen, um zu sehen, was in anderen Programmiersprachen m\u00f6glich ist und ob man es vielleicht f\u00fcr sich selbst adaptieren kann.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Einige Programmiersprachen bieten ein Feature mit dem etwas eigenartigen Namen \u201cDucktyping\u201d. Java z\u00e4hlt leider nicht dazu. In diesem Artikel m\u00f6chte ich kurz erkl\u00e4ren, was Ducktyping ist und wie man mit den in Java 8 eingef\u00fchrten Methodenreferenzen zumindest einen \u00e4hnlichen Effekt erzielen kann.<\/p>\n","protected":false},"author":18,"featured_media":1278,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"advgb_blocks_editor_width":"","advgb_blocks_columns_visual_guide":"","footnotes":""},"categories":[15],"tags":[218,237,438,439,440,441],"topics":[],"class_list":["post-1030","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-java","tag-java","tag-programmiersprache","tag-ducktyping","tag-java-methodenreferenzen","tag-interfaces","tag-typisierung"],"acf":[],"yoast_head":"<!-- This site is optimized with the Yoast SEO plugin v24.0 - https:\/\/yoast.com\/wordpress\/plugins\/seo\/ -->\n<title>Ducktyping &amp; Java 8 Methodenreferenzen - ZEISS Digital Innovation Blog<\/title>\n<meta name=\"description\" content=\"In diesem Beitrag wird erl\u00e4utert, was Ducktyping ist und wie man mit den in Java 8 eingef\u00fchrten Methodenreferenzen einen \u00e4hnlichen Effekt erzielen kann.\" \/>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/\" \/>\n<meta property=\"og:locale\" content=\"de_DE\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"Ducktyping &amp; Java 8 Methodenreferenzen - ZEISS Digital Innovation Blog\" \/>\n<meta property=\"og:description\" content=\"In diesem Beitrag wird erl\u00e4utert, was Ducktyping ist und wie man mit den in Java 8 eingef\u00fchrten Methodenreferenzen einen \u00e4hnlichen Effekt erzielen kann.\" \/>\n<meta property=\"og:url\" content=\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/\" \/>\n<meta property=\"og:site_name\" content=\"Digital Innovation Blog\" \/>\n<meta property=\"article:publisher\" content=\"https:\/\/www.facebook.com\/ZEISSDigitalInnovation\/\" \/>\n<meta property=\"article:published_time\" content=\"2015-10-26T14:09:06+00:00\" \/>\n<meta property=\"article:modified_time\" content=\"2020-06-17T10:33:15+00:00\" \/>\n<meta property=\"og:image\" content=\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-content\/uploads\/sites\/2\/2015\/10\/201510_ducktyping.png\" \/>\n\t<meta property=\"og:image:width\" content=\"640\" \/>\n\t<meta property=\"og:image:height\" content=\"426\" \/>\n\t<meta property=\"og:image:type\" content=\"image\/png\" \/>\n<meta name=\"author\" content=\"Manuel Mauky\" \/>\n<meta name=\"twitter:card\" content=\"summary_large_image\" \/>\n<meta name=\"twitter:creator\" content=\"@ZEISS_di\" \/>\n<meta name=\"twitter:site\" content=\"@ZEISS_di\" \/>\n<meta name=\"twitter:label1\" content=\"Verfasst von\" \/>\n\t<meta name=\"twitter:data1\" content=\"Manuel Mauky\" \/>\n\t<meta name=\"twitter:label2\" content=\"Gesch\u00e4tzte Lesezeit\" \/>\n\t<meta name=\"twitter:data2\" content=\"10\u00a0Minuten\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\/\/schema.org\",\"@graph\":[{\"@type\":\"WebPage\",\"@id\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/\",\"url\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/\",\"name\":\"Ducktyping & Java 8 Methodenreferenzen - ZEISS Digital Innovation Blog\",\"isPartOf\":{\"@id\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/#website\"},\"primaryImageOfPage\":{\"@id\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/#primaryimage\"},\"image\":{\"@id\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/#primaryimage\"},\"thumbnailUrl\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-content\/uploads\/sites\/2\/2015\/10\/201510_ducktyping.png\",\"datePublished\":\"2015-10-26T14:09:06+00:00\",\"dateModified\":\"2020-06-17T10:33:15+00:00\",\"author\":{\"@id\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/#\/schema\/person\/d7a29c5e55882a2841cfd79b4118132f\"},\"description\":\"In diesem Beitrag wird erl\u00e4utert, was Ducktyping ist und wie man mit den in Java 8 eingef\u00fchrten Methodenreferenzen einen \u00e4hnlichen Effekt erzielen kann.\",\"breadcrumb\":{\"@id\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/#breadcrumb\"},\"inLanguage\":\"de\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/\"]}]},{\"@type\":\"ImageObject\",\"inLanguage\":\"de\",\"@id\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/#primaryimage\",\"url\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-content\/uploads\/sites\/2\/2015\/10\/201510_ducktyping.png\",\"contentUrl\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-content\/uploads\/sites\/2\/2015\/10\/201510_ducktyping.png\",\"width\":640,\"height\":426},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Home\",\"item\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"Ducktyping &#038; Java 8 Methodenreferenzen\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/#website\",\"url\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/\",\"name\":\"Digital Innovation Blog\",\"description\":\"\",\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"de\"},{\"@type\":\"Person\",\"@id\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/#\/schema\/person\/d7a29c5e55882a2841cfd79b4118132f\",\"name\":\"Manuel Mauky\",\"image\":{\"@type\":\"ImageObject\",\"inLanguage\":\"de\",\"@id\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/#\/schema\/person\/image\/\",\"url\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-content\/uploads\/sites\/2\/2024\/06\/Mauky_Manuel_Profilbild_300x300px-150x150.jpg\",\"contentUrl\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-content\/uploads\/sites\/2\/2024\/06\/Mauky_Manuel_Profilbild_300x300px-150x150.jpg\",\"caption\":\"Manuel Mauky\"},\"description\":\"Manuel arbeitet seit 2010 als Softwareentwickler bei der ZEISS Digital Innovation in G\u00f6rlitz. Neben Java besch\u00e4ftigt er sich vor allem mit JavaScript und TypeScript und der Entwicklung von modernen Webanwendungen. Au\u00dferdem interessiert er sich f\u00fcr Funktionale Programmierung und h\u00e4lt regelm\u00e4\u00dfig Vortr\u00e4ge zu diesen Themen. Manuel hat in G\u00f6rlitz Informatik studiert und organisiert die Java-User-Group G\u00f6rlitz.\",\"url\":\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/author\/manuelmauky\/\"}]}<\/script>\n<!-- \/ Yoast SEO plugin. -->","yoast_head_json":{"title":"Ducktyping & Java 8 Methodenreferenzen - ZEISS Digital Innovation Blog","description":"In diesem Beitrag wird erl\u00e4utert, was Ducktyping ist und wie man mit den in Java 8 eingef\u00fchrten Methodenreferenzen einen \u00e4hnlichen Effekt erzielen kann.","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/","og_locale":"de_DE","og_type":"article","og_title":"Ducktyping & Java 8 Methodenreferenzen - ZEISS Digital Innovation Blog","og_description":"In diesem Beitrag wird erl\u00e4utert, was Ducktyping ist und wie man mit den in Java 8 eingef\u00fchrten Methodenreferenzen einen \u00e4hnlichen Effekt erzielen kann.","og_url":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/","og_site_name":"Digital Innovation Blog","article_publisher":"https:\/\/www.facebook.com\/ZEISSDigitalInnovation\/","article_published_time":"2015-10-26T14:09:06+00:00","article_modified_time":"2020-06-17T10:33:15+00:00","og_image":[{"width":640,"height":426,"url":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-content\/uploads\/sites\/2\/2015\/10\/201510_ducktyping.png","type":"image\/png"}],"author":"Manuel Mauky","twitter_card":"summary_large_image","twitter_creator":"@ZEISS_di","twitter_site":"@ZEISS_di","twitter_misc":{"Verfasst von":"Manuel Mauky","Gesch\u00e4tzte Lesezeit":"10\u00a0Minuten"},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"WebPage","@id":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/","url":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/","name":"Ducktyping & Java 8 Methodenreferenzen - ZEISS Digital Innovation Blog","isPartOf":{"@id":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/#website"},"primaryImageOfPage":{"@id":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/#primaryimage"},"image":{"@id":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/#primaryimage"},"thumbnailUrl":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-content\/uploads\/sites\/2\/2015\/10\/201510_ducktyping.png","datePublished":"2015-10-26T14:09:06+00:00","dateModified":"2020-06-17T10:33:15+00:00","author":{"@id":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/#\/schema\/person\/d7a29c5e55882a2841cfd79b4118132f"},"description":"In diesem Beitrag wird erl\u00e4utert, was Ducktyping ist und wie man mit den in Java 8 eingef\u00fchrten Methodenreferenzen einen \u00e4hnlichen Effekt erzielen kann.","breadcrumb":{"@id":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/#breadcrumb"},"inLanguage":"de","potentialAction":[{"@type":"ReadAction","target":["https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/"]}]},{"@type":"ImageObject","inLanguage":"de","@id":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/#primaryimage","url":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-content\/uploads\/sites\/2\/2015\/10\/201510_ducktyping.png","contentUrl":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-content\/uploads\/sites\/2\/2015\/10\/201510_ducktyping.png","width":640,"height":426},{"@type":"BreadcrumbList","@id":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/ducktyping-und-java-8-methodenreferenzen\/#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/"},{"@type":"ListItem","position":2,"name":"Ducktyping &#038; Java 8 Methodenreferenzen"}]},{"@type":"WebSite","@id":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/#website","url":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/","name":"Digital Innovation Blog","description":"","potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"de"},{"@type":"Person","@id":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/#\/schema\/person\/d7a29c5e55882a2841cfd79b4118132f","name":"Manuel Mauky","image":{"@type":"ImageObject","inLanguage":"de","@id":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/#\/schema\/person\/image\/","url":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-content\/uploads\/sites\/2\/2024\/06\/Mauky_Manuel_Profilbild_300x300px-150x150.jpg","contentUrl":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-content\/uploads\/sites\/2\/2024\/06\/Mauky_Manuel_Profilbild_300x300px-150x150.jpg","caption":"Manuel Mauky"},"description":"Manuel arbeitet seit 2010 als Softwareentwickler bei der ZEISS Digital Innovation in G\u00f6rlitz. Neben Java besch\u00e4ftigt er sich vor allem mit JavaScript und TypeScript und der Entwicklung von modernen Webanwendungen. Au\u00dferdem interessiert er sich f\u00fcr Funktionale Programmierung und h\u00e4lt regelm\u00e4\u00dfig Vortr\u00e4ge zu diesen Themen. Manuel hat in G\u00f6rlitz Informatik studiert und organisiert die Java-User-Group G\u00f6rlitz.","url":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/author\/manuelmauky\/"}]}},"author_meta":{"display_name":"Manuel Mauky","author_link":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/author\/manuelmauky\/"},"featured_img":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-content\/uploads\/sites\/2\/2015\/10\/201510_ducktyping-600x399.png","coauthors":[],"tax_additional":{"categories":{"linked":["<a href=\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/category\/java\/\" class=\"advgb-post-tax-term\">Java<\/a>"],"unlinked":["<span class=\"advgb-post-tax-term\">Java<\/span>"]},"tags":{"linked":["<a href=\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/category\/java\/\" class=\"advgb-post-tax-term\">Java<\/a>","<a href=\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/category\/java\/\" class=\"advgb-post-tax-term\">Programmiersprache<\/a>","<a href=\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/category\/java\/\" class=\"advgb-post-tax-term\">Ducktyping<\/a>","<a href=\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/category\/java\/\" class=\"advgb-post-tax-term\">Java Methodenreferenzen<\/a>","<a href=\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/category\/java\/\" class=\"advgb-post-tax-term\">Interfaces<\/a>","<a href=\"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/category\/java\/\" class=\"advgb-post-tax-term\">Typisierung<\/a>"],"unlinked":["<span class=\"advgb-post-tax-term\">Java<\/span>","<span class=\"advgb-post-tax-term\">Programmiersprache<\/span>","<span class=\"advgb-post-tax-term\">Ducktyping<\/span>","<span class=\"advgb-post-tax-term\">Java Methodenreferenzen<\/span>","<span class=\"advgb-post-tax-term\">Interfaces<\/span>","<span class=\"advgb-post-tax-term\">Typisierung<\/span>"]}},"comment_count":"0","relative_dates":{"created":"Posted 11\u00a0Jahren ago","modified":"Updated 6\u00a0Jahren ago"},"absolute_dates":{"created":"Posted on Oktober 26, 2015","modified":"Updated on Juni 17, 2020"},"absolute_dates_time":{"created":"Posted on Oktober 26, 2015 2:09 p.m.","modified":"Updated on Juni 17, 2020 10:33 a.m."},"featured_img_caption":"","series_order":"","_links":{"self":[{"href":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-json\/wp\/v2\/posts\/1030","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-json\/wp\/v2\/users\/18"}],"replies":[{"embeddable":true,"href":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-json\/wp\/v2\/comments?post=1030"}],"version-history":[{"count":4,"href":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-json\/wp\/v2\/posts\/1030\/revisions"}],"predecessor-version":[{"id":1279,"href":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-json\/wp\/v2\/posts\/1030\/revisions\/1279"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-json\/wp\/v2\/media\/1278"}],"wp:attachment":[{"href":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-json\/wp\/v2\/media?parent=1030"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-json\/wp\/v2\/categories?post=1030"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-json\/wp\/v2\/tags?post=1030"},{"taxonomy":"topics","embeddable":true,"href":"https:\/\/blogs.zeiss.com\/digital-innovation\/de\/wp-json\/wp\/v2\/topics?post=1030"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}