Ich habe aktuell beruflich wenig mit PHP zu schaffen, erklärt wohl auch die momentane Post-Flaute etwas. Joa, der angenehme Nebeneffekt davon ist aber, dass man beim Rumschlagen mit anderen Sprachen auch andere Konzepte verinnerlicht. So bin ich im Microsoft C# – Umfeld auf LINQ gestoßen. Bedeutet Language INtegrated Query. Was erstmal so unspektakulär klingt, ist eine verdammt mächtige Abfragesprache für Container (Arrays, Listen, Collections …).
LINQ?
string[] colors = new string[] { "Red", "Green", "Blue", "Blue", "Brown", "Pink", "Black" }; var result = (from c in colors where c.StartsWith("B") && c.Contains("l") && c.Length > 3 orderby c descending select c).Distinct(); foreach (var color in result) { Console.WriteLine(color); } /* Blue Black */
Als ich das das erste mal gesehen hab, saß ich schon etwas mit offenem Mund da. Abgesehen von der Anordnung der Kontrukte from / where / order by / select sieht das schon sehr nach SQL aus. Keine 5-fach verschachtelten Schleifen mehr, um auf komplexen Strukturen irgendwas zu errechnen / suchen. Auch Aggregationsfunktionen und sogar Joins hauen damit hin. Dadurch, dass LINQ fest mit der Sprache verbandelt ist, gibt es auch direkt beim Programmieren der Query schon Fehlerhinweise. Dabei ist nur eine einzige include-Direktive nötig und die ganze Magie steht zur Verfügung:
using System.Linq;
Und PHP?
Nagut, einen komplett PHP-freier Post ists nun doch nicht. Denn es gibt auch PHPLinq. Logischerweise muss es sich dabei um eine Eigenbaulösung handeln, die das C# – LINQ – Verhalten zu simulieren versucht. Schließlich kennt PHP von Grund auf solche Konstukte nicht. In 16 Dateien und 120 KB wird also Gas gegeben.
Ich klaue mal frech ein kleines Codebeispiel von der Examples-Seite:
require_once 'PHPLinq/LinqToObjects.php'; $names = array("John", "Peter", "Joe", "Patrick", "Donald", "Eric"); $result = from('$name')->in($names)->where('$name => strlen($name) < 5')->select('$name'); print_r($result);
Die Jungs haben sich also schon Mühe gegeben. Mehr Verwendungsbeispiele gibts in den im Download enthaltenen Tests. Aber mal ehrlich… So richtig könnte ich mich im Produktiveinsatz nicht dran gewöhnen. Das geht schon damit los, dass ich erst zur Laufzeit sehen kann, ob es einen Fehler gab. Und dann ists halt trotz allem noch ein externes Paket. Aber gut, es mal gesehen zu haben.
Ich kann mir grade mal kein Szenario vorstellen, wo es sich lohnt so was zu verwenden. Wenn ich komplexe Daten habe, dann nutze ich eine Datenbank – die können das von Haus aus.
Und wenn ich mal ein Array nach Kriterien filtern muss, dann bin ich wahrscheinlich performancetechnisch mit einer foreach Schleife besser bedient als mit so einer Klasse, oder? Schön, es mal gesehen zu haben, aber weitgehend sinnfrei. *schulter-zuck*
Ich habe gerade etwas mehr mit Java zu tun und vermisse Linq da an der einen oder anderen Stelle schon.
@Oliver: Es ist ja auch nicht so, dass Linq nur für das Durchsuchen von Arrays taugt. Genauso kann man mit Linq to Entities bzw. Linq to SQL abfragen auf die Datenbank bzw. seinen OR-Mapper machen. Das alles dann auch noch typsicher weil ja „Language integrated“.
Davon abgesehen könnte ich mir vorstellen (habe es aber nicht recherchiert), dass Linq auch etwas elegantere Suchalgorithmen als eine for-Schleife (z.B. für das Suchen in sortierten Mengen ?) verwendet.
Edit:
OK nachdem ich meine Vermutung mit der Performance mal eben gegoogelt habe muss ich sie gleich wieder verwerfen. Linq scheint etwas langsamer zu sein (syntactic sugar eben) aber nicht in einer Größenordnung die für die meisten relevant sein düfte.
Dafür bringe ich noch ein anderen Argument für Linq. Egal welche Datenquelle man nun durchsucht (Datenbank, Collection, XML-Dokument) man benutzt SQL-ähnliche Befehle. die die meisten ohnehin lesen können, und macht den Code dadurch verständlicher/besser lesbar.
Ich nutz ein Framework und habe in den letzten 10 Jahren irgendwie keine komplexen Arrays gebraucht. :-)
Interessant. Ich dachte, dass der Compiler im Stande ist, aus einer LINQ Query was performanteres zu machen als das bei 4 verschachtelten for-Schleifen der Fall ist. Kannst du die Quelle dafür hier reinhaun?
Nun wie das bei 4 verschachtelten aussieht kann ich auch nicht sagen. Aber wenn man z.B. „linq vs loop performance“ googlet bekommt man einige Ergebnisse bei denen das getestet wurde.
LINQ ist auch nicht dafür da um Array zu durchsuchen, es ist nur eine der möglichen Anwendungen. Es ist einfach nur eine Methode um einheitlich Objekte zu traversieren.
Im Entity Framework z. Bsp. wird aus einem LINQ Statement SQL generiert der Vorteil dabei ist, dass man kein SQL als Text im Code hat und im Fehlerfall wird es nicht mal kompilieren und für die Entwickler von EF war der Vorteil, dass die keine neue Sprache erfinden mussten um Ihre Queries validierbar zu machen.
Es ist halt ein Werkzeug, richtig eingesetzt ist es effektiv ansonsten ist das handlich.
Man kann an der Stelle hier genau so darüber philosophieren ob eine loop, for oder each Schleife besser sei.
aruss