„Verschieben Sie nie bis zur Laufzeit, was zur Kompilierzeit erledigt werden kann.“
David Gries, Compilerkonstruktion für digitale Computer
Einführung
Als Programmierer können Beispiele manchmal unser größter Feind sein, wenn wir neue Technologien erlernen. Richtlinien sind oft so gestaltet, dass sie einfach und leicht verständlich sind, können aber gleichzeitig zu einer Zunahme von trägem, ineffizientem und sogar gefährlichem Code-Schreiben führen. Die häufigste Situation wie diese kommt im ADO.NET-Paradigma vor. In diesem Artikel werfen wir einen Blick darauf, was es bedeutet, stark typisierte Objekte in einer Datenbank zu haben, damit Sie dies trotz fehlender Beispiele in Ihren Programmen tun können.
Etwas genauer werden wir sehen, wie stark typisierte Datensätze in Visual Studio 2005 erstellt und verwendet werden. Wie in diesem Artikel untersucht wird, bieten stark typisierte Datensätze viele Vorteile gegenüber anderen schwach typisierten Datenzugriffstechniken. Wir werden hier auch sehen, dass das Erstellen und Verwenden stark typisierter Datensätze mit Visual Studio 2005 nicht einfacher wird. Wenn Sie mehr erfahren möchten, lesen Sie weiter.
Die Grundlagen und Vorteile stark typisierter Objekte
Um zu verstehen, was starkes Typisieren bedeutet, können Sie zunächst über Dating nachdenken. Wenn Sie Single wären, welche Art von Person würden Sie für ein Date in Betracht ziehen? Möglicherweise haben Sie bestimmte Kriterien (z. B. gesund und attraktiv) oder die Kriterien sind einfach oder unklar. Unabhängig von Ihren Bedingungen werden Sie bei der Entscheidung, mit wem Sie mehr Zeit verbringen möchten, immer Ihre eigenen, bestimmten Standards für diese Typen zum Abwägen und Berücksichtigen heranziehen. Wenn Sie schlau sind, werden Sie viel nachdenken, um sich vor emotionalen Traumata zu schützen. Möglicherweise stellen Sie beispielsweise fest, dass das Zusammenleben mit einem Alkoholiker instabil ist, es sei denn, die beiden führen eine ernsthafte Beziehung. Es ist jedoch schmerzhaft und sehr schwierig, eine Person dazu zu bringen, sich zu ändern. Daher wird Ihre Weisheit Sie anweisen, die Beziehung zu beenden, bevor sie überhaupt begonnen hat. Das Hinzufügen einer Verbotsklausel zu Ihren Dating-Kriterien schützt Sie vor zukünftigem Kummer und ermöglicht es Ihnen, Ihre Zeit und Energie auf bessere Kandidaten zu konzentrieren.
Sie werden überrascht sein, dass diese Argumentation etwas mit der Programmierung zu tun hat. Es spielt keine Rolle, komm mit mir, liebe Leserin! ADO.NET-Datenzugriffsobjekte sind äußerst flexibel konzipiert. Wenn Sie Daten aus einer Datenbank lesen, arbeiten Sie wahrscheinlich mit vielen der gängigen Objekttypen, die das normale .NET-Framework zulässt, sofern Sie nicht auf spezielle Probleme stoßen. Wenn Sie unsere Datierungstheorie anwenden, können Sie sich Ihre relevanten Daten grundsätzlich als universelle Objekte vorstellen. „Solange mein Date keine allzu großen Probleme bereitet.“ Kannst du das nicht klarer ausdrücken? Es gibt keine Begrenzung, auch wenn es sich um einen Menschen oder ein anderes Lebewesen handelt! Als Ihr Freund flehe ich Sie an: „Mehr Standards! Machen Sie Ihre Liste kleiner!“
So wie es in der Zukunft zu Beziehungsproblemen führen kann, wenn Sie vernachlässigen, mit wem Sie sich verabreden, kann es auch zu Fehlern führen, wenn Sie Ihre Objekte in Ihrem Code nicht markieren. Wenn Sie außerdem alte Objekte in Ihrer Unterroutine herumwandern lassen, bemerken Sie das Problem möglicherweise erst, wenn das Programm ausgeführt wird. Um unsere Dating-Theorie zu nutzen, ist das Erkennen von Fehlern zur Laufzeit so, als ob Ihr Date mitten in einem angesagten italienischen Restaurant einen schmerzhaften und unangenehmen Streit ausführt. Ja, wissen Sie, wenn Sie im Voraus geplant hätten, wären Sie nicht von einer Gruppe von Gästen angestarrt worden, und es wäre auch nicht peinlich gewesen. Indem Sie einfach einige strengere Standards auf Ihren Code anwenden, können Sie Fehler erkennen, bevor Ihr Programm mit der Kompilierung beginnt. Zum Beispiel das folgende Codebeispiel:
string FirstName = myrow.("FirstName").ToString();
Die DataRow in diesem Beispiel ist untypisiert. Daher müssen Sie den Spaltennamen als Zeichenfolge verwenden, um den benötigten Wert zu erhalten (oder Sie können den Index der Spalte in der Spaltensammlung des Datensatzes verwenden). Glücklicherweise existiert diese Spalte. Der Datentyp der Spalte „DataRow“ ist Objekt. Wir gehen davon aus, dass der Datentyp unter der Spalte „Vorname“ ein String ist, und wir müssen ihn vor der Verwendung explizit in einen String konvertieren. Wenn sich der Name dieser Spalte ändert (z. B. zu PersonFirstName), hat der Compiler keine Möglichkeit, Sie zu benachrichtigen. Gedrückt? Aber das musst du nicht. Wenn Ihr Code wie folgt aussieht, wird Ihr Leben einfacher und Ihr Code zuverlässiger.
string FirstName = PersonRow.FirstName;
In diesem zweiten Beispiel verwenden wir eine stark typisierte Zeile und wissen, dass die FirstName-Eigenschaft vom Typ string ist. Keine unordentlichen Spaltennamen, keine unordentlichen Typkonvertierungen. Der Compiler hat die Typprüfung bereits für uns durchgeführt, und wir können sicher andere Arbeiten ausführen, ohne uns Gedanken darüber machen zu müssen, ob wir die Spaltennamen richtig eingegeben haben.
Alles andere ist gleich, Sie werden also nicht zögern, diesen anstelle des generischen Typs zu verwenden. Aber Moment mal, woher kommen stark typisierte Objekte? Ich wünschte, ich könnte Ihnen auch sagen, dass diese Objekte automatisch erstellt werden. Aber genauso wie gute Beziehungen Zeit und Mühe erfordern, erfordert es zusätzlichen Aufwand, Ihren Objekten eine starke Typisierung zu verleihen. Aber die hier aufgewendete zusätzliche Zeit lohnt sich auf jeden Fall und spart in Zukunft exponentiell mehr Zeit für das „Fangen von Fehlern“.
Es gibt mehrere Möglichkeiten, eine starke Typisierung zu erreichen, und wir werden den Rest dieses Artikels damit verbringen, zu erklären, wie man einen stark typisierten Datensatz in Visual Studio 2005 erstellt. Wir werden auch die Vor- und Nachteile dieses Ansatzes mit anderen Ansätzen vergleichen.
Erstellen stark typisierter Datensätze in Visual Studio 2005
Stark typisierte Datensätze sind eigentlich nur vordefinierte Spalten und Tabellen gewöhnlicher Datensätze, sodass der Compiler bereits weiß, was sie enthalten. Statt einer losen Hülle, die Ihnen wie ein Baseballhandschuh passt, passen stark typisierte Datensätze wie angegossen. Jede nachfolgende Version von Visual Studio erleichtert den Umgang mit stark typisierten Datensätzen. Im folgenden Beispiel verwenden wir die AdventureWorks-Datenbank von SQL Server 2005. Befolgen Sie einfach diese Schritte:
1. Öffnen Sie Visual Studio und erstellen Sie eine neue ASP.NET-Website.
2. Klicken Sie im Projektmappen-Explorer-Fenster mit der rechten Maustaste, um ein neues Element hinzuzufügen, und wählen Sie DataSet aus. Nennen Sie es AdventureWorks.xsd (siehe Screenshot). Visual Studio empfiehlt, dass Sie die DataSet-Datei in die App_Code-Datei einfügen und einfach auf „Akzeptieren“ klicken.
3. Nach dem Öffnen von AdventureWorks.xsd im Designmodus wird der TableAdapter-Konfigurationsassistent ausgeführt. Klicken Sie an dieser Stelle auf „Abbrechen“ und wir ziehen die gewünschte Tabelle aus dem Server-Explorer hinein.
4. Suchen Sie in der Symbolleiste des Server-Explorers nach der AdventureWorks-Datenbank. (Wenn Sie die AdventureWorks-Datenbank nicht installiert haben, können Sie sie und einige andere SQL Server 2005-Beispiele auf der Downloadseite „SQL Server 2005-Beispiele und Beispieldatenbanken“ von Microsoft herunterladen.)
5. Ziehen Sie die Tabellen SalesOrderHeader und SalesOrderDetail in das DataSet-Designfenster. Das Fenster sollte wie im Screenshot aussehen. Was sehen wir? Immer wenn wir eine Tabelle hinzufügen, erstellt Visual Studio eine stark typisierte DataTable (mit demselben Namen wie die Originaltabelle) und einen TableAdapter. Diese DataTable hat jede Spalte für uns definiert. TableAdapter verwenden wir zum Füllen der Tabelle. Standardmäßig gibt es eine Fill()-Methode, um jede Datenzeile aus der Originaltabelle abzurufen.
So wie es ist, gibt dieser stark typisierte Datensatz alle Datensätze aus beiden Tabellen zurück. Aber die AdventureWorks-Datenbank enthält viele Bestellinformationen. Warum also nicht eine explizitere Abfrage erstellen? Wir können dem TableAdapter-Objekt Methoden hinzufügen, um einen bestimmten Unterdatensatz zu erhalten. Klicken Sie mit der rechten Maustaste auf SalesORderHeaderTableAdapter und wählen Sie Hinzufügen|Abfrage aus. Wählen Sie „SQL-Anweisungen verwenden“ und klicken Sie auf „Weiter“. Wählen Sie dann „AUSWÄHLEN, das Zeilen zurückgibt“ und klicken Sie auf „Weiter“. Geben Sie kürzlich die folgende Abfrage in das Fenster ein (oder verwenden Sie Query Builder, um die Aufgabe zu erledigen):
WÄHLEN
SalesOrderID, RevisionNumber, OrderDate, DueDate, ShipDate,
Status, OnlineOrderFlag, SalesOrderNumber, PurchaseOrderNumber,
AccountNumber, CustomerID, ContactID, SalesPersonID, TerritoryID,
BillToAddressID, ShipToAddressID, ShipMethodID, CreditCardID,
CreditCardApprovalCode, CurrencyRateID, SubTotal, TaxAmt, Freight,
TotalDue, Comment, rowguid, ModifiedDate
FROM Sales.SalesOrderHeader
WHERE (OrderDate > @OrderDate)
Diese SQL-Abfrage ist eine einfache SELECT-Abfrage, die einen @OrderDate-Parameter zum Filtern der Ergebnisse verwendet. Dies erspart uns die Rückgabe aller Datensätze in der Datenbank. Lassen Sie die Kontrollkästchen „Eine Datentabelle füllen“ und „Eine Datentabelle zurückgeben“ aktiviert und klicken Sie auf „Fertig stellen“. Nachdem Sie diese SELECT-Anweisung hinzugefügt haben, sollte Ihr Designer nun wie im Screenshot aussehen, mit einer zusätzlichen Abfrage unter SalesOrderHeaderTableAdapter.
Nachdem der stark typisierte Datensatz erstellt wurde, können wir die Daten mit wenigen Codezeilen problemlos auf der ASP.NET-Seite anzeigen. Erstellen Sie eine neue ASP.NET-Seite auf der Website und wechseln Sie in den Designmodus. Ziehen Sie ein GridView-Steuerelement darauf und belassen Sie seine ID bei GirdView1. Gehen Sie dann zur Quellcodeseite und führen Sie den AdventureWorksTableAdapters-Namespace über der Datei ein (die Syntax in c# verwendet AdventureWorksTableAdapters;). Fügen Sie abschließend den folgenden Code zum Page_Load-Ereignis hinzu:
// Den SalesOrderHeaderTableAdapter erstellen
SalesOrderHeaderTableAdapter salesAdapter =
new SalesOrderHeaderTableAdapter();
// Bestellungen abrufen, die nach dem 1. Juli 2004 erfolgten
AdventureWorks.SalesOrderHeaderDataTable Orders =
salesAdapter.GetDataBy(new DateTime(2004, 7, 1));
// Die Bestellergebnisse an die GridView binden
this.GridView1.DataSource = Bestellungen;
this.GridView1.DataBind();
Der Code ist sehr einfach. Wir erstellen eine Instanz von SalesORderHeaderTableAdapter, um die Datentabelle zu füllen. Hierbei ist zu beachten, dass wir im Gegensatz zu einer gewöhnlichen DataTable ein Objekt vom Typ SalesORderHeaderDataTable deklarieren. Wir rufen die Methode GetDateBy() auf und übergeben ein DateTime-Objekt, um die Daten einzugeben. Beachten Sie auch hier, dass der erhaltene Befehl ebenfalls stark typisiert ist, sodass wir ein DateTime-Objekt anstelle eines gewöhnlichen Objekts übergeben müssen. Der folgende Screenshot ist das Ergebnis des obigen Codebeispiels.
Zusätzlich zur Verwendung von Code zum Binden des Ergebnissatzes an GridView können Sie auch eine ObjectDataSource verwenden, deren TypeName-Eigenschaft auf AdventureWorksTableAdapters.SalesOrderHeaderTableAdapter und deren SelectMethod auf GetData oder GetDataBy festlegen.
Ein weiterer großer Vorteil der Verwendung eines stark typisierten Datensatzes besteht nicht nur darin, dass für die Verbindung mit der Datenbank kein Code geschrieben werden muss, sondern auch darin, dass in unserem Code keine Spaltennamenszeichenfolgen lauern, die der Compiler nicht überprüfen kann. Wir müssen auch keine Typkonvertierung durchführen. Wenn sich das Datenbankschema ändert, aktualisieren Sie einfach die Datei AdventureWorks.xsd und wir werden feststellen, dass alle damit verbundenen Änderungen zur Kompilierungszeit automatisch abgeschlossen werden.
Andere Techniken zum Generieren stark typisierter Datenzugriffsanwendungen
Neben der Verwendung stark typisierter Datensätze gibt es noch andere Möglichkeiten, starke Typisierung in Ihren Programmen zu implementieren. Sie können benutzerdefinierte Klassen erstellen, die einfacher als DataSets und konsistenter mit Ihrer Datenbank sind. Es gibt auch einige Softwareentwickler von Drittanbietern, die Tools zur Automatisierung dieses Prozesses entwickelt haben. Eines der spezielleren und mein Favorit ist LLBLGen Pro. Ich habe einmal ein Buch darüber geschrieben: Rapid C# Windows Development: Visual Studio 2005, SQL Server 2005, and LLBLGen Pro. (Sie können 1/3 des Buches kostenlos auf meiner Website lesen.) Ein weiteres beliebtes Tool ist CodeSmith. Sogar Microsoft entwickelt ein kleines Tool namens DLINQ, das jedoch noch getestet wird und voraussichtlich erst im nächsten Jahr auf den Markt kommen wird.
Wenn Sie den starken Datensatzansatz von Visual Studio nutzen, besteht einer der unbestreitbaren Vorteile darin, dass Sie keine zusätzliche Software kaufen müssen. Alle diese Lösungen haben unterschiedliche Funktionen und Vorteile, aber die Hauptvorteile sind Zuverlässigkeit, weniger Fehler und weniger Zeitaufwand für die Fehlerbehebung. Außerdem ist es einfacher, die Auswirkungen von Datenbankschemaänderungen zu überprüfen und Wartungsarbeiten durchzuführen. Hoffentlich haben Sie die Vorteile des starken Tippens erkannt. Viel Glück bei der Entwicklung (und auch beim Dating)!
Von Joseph Chancellor
Attachments
Laden Sie den in diesem Artikel untersuchten Code herunter
Über den Autor
Joseph Chancellor ist ein C#-Entwickler aus Südkalifornien, der einiges an relationalem Trauma erlebt hat. Besuchen Sie seinen Blog oder lesen Sie die ersten fünf Kapitel seines Buches über Visual Studio 2005, SQL Server 2005 und LLBLGen Pro.
Ursprüngliche Adresse: http://aspnet.4guysfromrolla.com/articles/020806-1.aspx