Programmierparadigmen Teil 1: Funktionale Programmierung Kapitel 4 Integration von Erlang & Java http://www.tu-ilmenau.de/fakia/Functional.html Programmierparadigmen Teil 1 (SS 17): 04 – Integration von Erlang & Java 1 Erlang vs. Java Unsere bisherigen Betrachtungen haben gezeigt, dass: zahlreiche Aufgaben sehr elegant in Erlang gelöst werden können, die Erlang-Umgebung die Realisierung sehr hoher Verfügbarkeitsanforderungen unterstützt man funktionale Programme per Induktionsbeweis verifizieren kann Allerdings auch: Manche Dinge können in Erlang nur „umständlich“ gelöst werden Erlang-Programme werden in der Regel weniger effizient ausgeführt als Java-Programme (oder insbesondere C, C++) Weiterhin gibt es für imperative Programmiersprachen wie Java zahlreiche sehr nützliche Bibliotheken, die einem viel Arbeit abnehmen können und zudem eigene Fehler (bei evtl. ReImplementierung) vermeiden helfen Es wäre daher gut, wenn in einem Projekt beide Sprachen gleichberechtigt eingesetzt werden könnten, so dass man die Stärken beider Ansätze nutzen kann, ohne unter den jeweiligen Schwächen zu leiden Programmierparadigmen Teil 1 (SS 17): 04 – Integration von Erlang & Java 2 Ansatz zur Integration von Erlang und Java Erlang unterstützt per Sprachdefinition den Austausch von Nachrichten zwischen Erlang-Prozessen Daher liegt es nahe, diese Kommunikationsmechanismen auch für die Integration von Erlang- und Java-Programmen zu nutzen: Für genau diesen Zweck wurde die Java-Bibliothek „jinterface“ entwickelt Sie ermöglicht Java-Programmen die Kommunikation mit ErlangProzessen Hierzu stellt sie Grundfunktionen für die Einrichtung einer Kommunikationsbeziehung sowie grundlegende Datenstrukturen für Erlang-ähnliche Datentypen und Mailboxen bereit Programmierparadigmen Teil 1 (SS 17): 04 – Integration von Erlang & Java 3 Ein einfacher Zähl-Server (1) import com.ericsson.otp.erlang.*; public class CounterServer { public static void main(String[] args) throws Exception { OtpNode myNode = new OtpNode("server@localhost"); OtpMbox myMbox = myNode.createMbox("counter"); Integer counter = 0; OtpErlangAtom myAtom = new OtpErlangAtom("ok"); // continued on next slide Programmierparadigmen Teil 1 (SS 17): 04 – Integration von Erlang & Java 4 Ein einfacher Zähl-Server (2) while(true) try { OtpErlangTuple myMsg = (OtpErlangTuple)myMbox.receive(); OtpErlangPid from = (OtpErlangPid)myMsg.elementAt(0); OtpErlangString command = (OtpErlangString)myMsg.elementAt(1); // here you may want to check the value of command OtpErlangObject[] reply = new OtpErlangObject[2]; reply[0] = myAtom; reply[1] = new OtpErlangInt(counter); OtpErlangTuple myTuple = new OtpErlangTuple(reply); myMbox.send(from, myTuple); counter++; } catch(OtpErlangExit e) { break; } } // of function main } // of class definition Programmierparadigmen Teil 1 (SS 17): 04 – Integration von Erlang & Java 5 Ein einfacher Zähl-Server (3) Client written in Erlang: -module(client). -export([count/0]). count()-> {counter, 'server@localhost'} ! {self(), "count"}, receive {ok, Counter} -> io:format("Counter is at value: ~p~n", [Counter]) end. Compile Java Code and start Erlang Port Mapper Daemon, give yourself a name : javac -classpath ".:/usr/local/lib/erlang/lib/ jinterface-1.5.4/priv/OtpErlang.jar" CounterServer.java epmd -daemon % in local erts\bin directory erl -sname "erlang@localhost" Programmierparadigmen Teil 1 (SS 17): 04 – Integration von Erlang & Java 6 Reflexion Das vorgehende Beispiel zeigt die bidirektionale Kommunikation zwischen einem Java- und einem Erlang-Prozess Grundsätzlich können beide Prozesse auch auf unterschiedlichen Rechnern laufen (führt zu zusätzlicher Latenz aufgrund von Nachrichtenlaufzeiten) Einzelheiten können in der Dokumentation und auf diversen Internet-Seiten nachgelesen werden (siehe auch Übung) Aber: verlieren wir durch diese zusätzlichen Möglichkeiten auch etwas? Der CounterServer liefert bei jedem Aufruf von count() ein anderes Resultat – das war ja explizit auch so gewünscht Damit verlieren wir leider die elementare Eigenschaft, dass Funktionen bei gleicher Eingabe immer das gleiche Resultat liefern Der Grund hierfür ist, dass das Senden und Empfangen von Nachrichten einen Seiteneffekt darstellt und Funktionen eigentlich keine Seiteneffekte haben sollten (→ Achtung bei Beweisen!) Grundsätzlich gilt das auch für reine Erlang-Programme, welche die Kommunikationsmechanismen verwenden Programmierparadigmen Teil 1 (SS 17): 04 – Integration von Erlang & Java 7