Eine Datenbankanwendung für Android

ASP.NET MVC – C++/CLI

Nachdem ich so eine tolle Möglichkeit gefunden habe, mit Boost in C++ so schön und schnell die Betweenness Centrality der Nomen eines Textes zu berechnen, könnte ich doch meine Studienbibel, die ich in ASP.NET MVC verfasst habe, mit dieser Möglichkeit erweitern. Bei meinem letzten Job hatte ich schon einmal die Verknüpfung von C# und C++ über C++/CLI gemeistert und ich will an diesen Erfolg anknüpfen. Auf meinem Rechner klappt das super. Ich erstelle eine gemischte managed/unmanaged DLL, welche über ein managed Interface für die C#-Assembly verfügt und darüber nativen Code ausführen kann. Aber als ich meine Anwendung auf den Server veröffentlichen will, wird beim Start der Ausführung aber eben jene gemischte DLL vermisst. Je mehr ich im Internet zu dem Problem recherchiere, desto mehr Lösungsmöglichkeiten eröffnen sich. Darunter finden sich doch recht viele Meinungen, wie höllisch kompliziert die Mischung C++ und c# mittels C++/CLI doch sei. Nachdem ich einen Sonntag geopfert habe und sich noch mehr Möglichkeiten und Unklarheiten auftun, halte ich inne. Das ist eben doch ein Nachteil an Microsoft. Wäre so ein Server frei, könnte ich ihn mir einfach herunterladen und in einer virtuellen Maschine laufen lassen und den ausgeführten Code auf dem Server per Debugger untersuchen. Die vielen einfachen Lösungsmöglichkeiten hatte ich natürlich ausprobiert, aber um hier weiter zu kommen, brauche ich mehr als spielerisches Interesse an technischen Herausforderungen. Ich bin eben doch kein Technokrat. Was will ich eigentlich? Muss ich unbedingt der Welt zeigen, dass ich ein C++/CLI-Spezialist sein könnte? Sinnlos! Ich will eine Studienbibel programmieren und cool wäre das doch eigentlich für Android! Dann wäre ich nicht vom Internet abhängig und könnte auch im Wald oder in sonstiger Natur die Bibel auf besondere und komfortable Weise lesen. Eben überall, wo ich gerade bin.

Android NDK

Ich probiere ein Hello-World-NDK-Beispiel unter Android aus. Um SQLite nativ zum Laufen zu bringen, muss ich die riesige SQLite C-Datei meinem Makefile hinzufügen und neu kompilieren. Dazu gibt es Beispiele und nach einigem Gefummel habe ich SQLite und die Boost/Graph-Bibliothek nativ unter Android am Laufen. Der Nachteil von nativen Programmen unter Android ist aber die Geschwindigkeit. Während es an meinem Desktop-Rechner eine halbe Sekunde dauert jedes Wort eines Bibelbuches inklusive seiner 10 Parameter aus der Datenbank einzulesen und aus den Worten der Nominalphrasen einen Graphen aufzubauen und die Betweenness-Centrality sowohl der Kanten als auch der Knoten des Graphes auszurechnen, sind es auf meinem schon betagten Nexus S ca. 30 Sekunden. Diese Geschwindigkeit ist nicht akzeptabel. Auch hier wieder: Was soll der Spieltrieb? Tatsächlich sagt auch die Android Developer-Doku, dass man schon einen triftigen Grund haben sollte, um nativ unter Android zu programmieren, da es mit Sicherheit die Komplexität der Entwicklung erhöht, nicht aber unbedingt die Geschwindigkeit der Ausführung. Muss es also unbedingt dynamisch sein? Es reicht doch, wenn ich vorher die Betweennes Centrality für Kanten und Knoten ausrechne und die Ergebnisse in der Datenbank festhalte. Bei der Bibel handelt es sich schließlich um statischen Inhalt und es ist nicht damit zu rechnen, dass noch mehr Inhalt hinzugefügt wird. Was seit tausenden von Jahren penibelst vor Veränderungen geschützt wurde, wird wahrscheinlich nicht plötzlich geändert werden. Wenn ich vorher die Zentralitäten ausrechne, kann ich dies sogar für die gesamte Bibel tun. Ich kann alle ca. 800.000 Worte der Bibel einlesen und einen Graphen über die gesamte Bibel aufbauen und errechne mir damit Worte, die bibelweit zentral sind. Wenn ich diese Zentralitäten für meine Studienbibel benutze, helfe ich dem Benutzer die Bibel im Überblick zu behalten.

Normalisiert vs. Unormalisiert

Soll ich nun meine Datenbank normalisieren oder unnormalisiert lassen. An jeder Informatik-Uni lernt man, dass man Daten in der Datenbank natürlich normalisieren sollte. Aber das gilt nur für Daten, die sich vermehren. Eine unnormalisierte Datenbank verschlingt zuviel Platz, da Einträge vielfach vorkommen können und die Datenbank schlecht gewartet werden kann. Andererseits spart man sich auch komplizierte Join-Anfragen. Wenn ich wirklich meine Datenbank normalisieren würde, würde ich aus der zentralen Tabelle 5 Tabellen machen und müsste damit über ein 5-fach verschlachteltes Join-Statement 5 Tabellen abfragen. Ich habe gehört, dass sich das nicht sonderlich positiv auf die Performance auswirkt. Allerdings werde ich das noch ausprobieren. Denn der Benutzer lädt sich auch nicht gerne 100 MB herunter. Allerdings muss ich meine SQLite-DB indexieren. Wenn ich einen Index über häufig gefragte Spalten erstelle, antwortet SQLite in akzeptabler Geschwindigkeit auf eine Abfrage. Andernfalls dauert es einige Sekunden, bei jeder Anfrage erneut 800.000 Datensätze durchsuchen zu müssen.