Erweiterte Programmierthemen: Klassenbibliotheken
Eine Klassenbibliothek (auch DLL genannt, für Dynamic Link Library) erlaubt die Auslagerung von Klassen und Namensräumen in einer separaten Datei. Hierbei erhalten wir nicht wie bei einer Konsolen-, Windows Forms- oder WPF-Anwendung eine .exe-Datei, sondern eine .dll-Datei. Beim Erstellen eines Projekts mit Visual Studio kann hierbei der Typ „Klassenbibliothek“ verwendet werden. Eine DLL kann nicht direkt ausgeführt werden, da diese keinen Einstiegspunkt besitzt. Somit handelt es sich bei einer DLL also um ein nicht ausführbares Programm. Jedoch können wir über Verweise oder einen Import DLLs in unser Programm einbinden.
Der Import von DLLs wird nur für Klassenbibliotheken benötigt, welche nicht in .NET-Sprachen (also C# oder Visual Basic) programmiert wurden (sondern z. B. in C oder C++). Hierfür müssen wir [DllImport("MeineDll.dll")] notieren. Unterhalb diesem sogenannten Attribut (also in der nächsten Zeile) erfolgt nun eine Funktionsdeklaration, jedoch mit dem Schlüsselwort extern, welches zwischen Zugriffsmodifizierer und Rückgabetyp angegeben werden muss. Zusätzlich muss der Namensraum System.Runtime.InteropServices per using-Schlüsselwort eingebunden werden.
Um eine .NET-Klassenbibliothek einzubinden, müssen wir über den Verweis-Explorer die DLL einbinden (mit Hilfe des „Dursuchen“-Reiters). Dabei wird die DLL beim Kompilieren automatisch in den bin/Debug oder bin/Release Ordner kopiert. Befindet sich unser Klassenbibliotheks-Projekt in der gleichen Projektmappe wie unsere Anwendung, in welcher wir diese verwenden wollen, so kann direkt ein Verweis auf ein Projekt der Projektmappe erstellt werden.
DLLs sind jedoch nicht nur für die Auslagerung und Strukturierung von Programmcode gedacht, sondern dienen vielmehr auch zur Wiederverwendung. So können Sie die gleiche DLL in verschiedenen Anwendungen einbinden und verwenden.
Das Beispiel zeigt einen einfachen Taschenrechner für zwei Zahlen. In der DLL gibt es Funktionen zur Berechnung (Plus, Minus, Mal und Geteilt) sowie Funktionen zur Prüfung der eingegebenen Zahl. Das Hauptprogramm enthält hingegen die Textfelder und Auswahlfelder. Über den Button-Klick wird die Checked-Eigenschaft der RadioButton-Steuerelemente überprüft und dementsprechend Funktionen der Klassenbibliothek aufgerufen.
Calculator.cs
namespace CSV20.Klassenbibliothek_Library { public class Calculator { public static int Addition(int iZahl1, int iZahl2) { return iZahl1 + iZahl2; } public static double Addition(double dZahl1, double dZahl2) { return dZahl1 + dZahl2; } public static int Subtraktion(int iZahl1, int iZahl2) { return iZahl1 - iZahl2; } public static double Subtraktion(double dZahl1, double dZahl2) { return dZahl1 - dZahl2; } public static int Multiplikation(int iZahl1, int iZahl2) { return iZahl1 * iZahl2; } public static double Multiplikation(double dZahl1, double dZahl2) { return dZahl1 * dZahl2; } public static int Division(int iZahl1, int iZahl2) { return iZahl1 / iZahl2; } public static double Division(double dZahl1, double dZahl2) { return dZahl1 / dZahl2; } } }
Number.cs
namespace CSV20.Klassenbibliothek_Library { public class Number { public static bool IsNumber(string sEingabe, out int iZahl) { return int.TryParse(sEingabe, out iZahl); } public static bool IsNumber(string sEingabe, out double dZahl) { return double.TryParse(sEingabe, out dZahl); } public static bool DivisionErlaubt(int iZahl) { return iZahl != 0; } public static bool DivisionErlaubt(double dZahl) { return dZahl != 0; } } }
Form1.cs
using System; using System.Windows.Forms; using CSV20.Klassenbibliothek_Library; namespace CSV20.Klassenbibliothek_Form { public partial class Form1 : Form { public Form1() { InitializeComponent(); } private void buttonBerechnen_Click(object sender, EventArgs e) { int iZahl1, iZahl2, iZahlErgebnis; double dZahl1, dZahl2, dZahlErgebnis; if (radioButtonGanz.Checked) { if (Number.IsNumber(textBoxZahl1.Text, out iZahl1)) { if (Number.IsNumber(textBoxZahl2.Text, out iZahl2)) { if (radioButtonAdd.Checked) iZahlErgebnis = Calculator.Addition(iZahl1, iZahl2); else if (radioButtonSub.Checked) iZahlErgebnis = Calculator.Subtraktion(iZahl1, iZahl2); else if (radioButtonMul.Checked) iZahlErgebnis = Calculator.Multiplikation(iZahl1, iZahl2); else // if (radioButtonDiv.Checked) { if (Number.DivisionErlaubt(iZahl2)) { iZahlErgebnis = Calculator.Division(iZahl1, iZahl2); } else { MessageBox.Show("Die Division ist mit der eingegebenen Zahl nicht möglich!", "Rechenoperation ungültig", MessageBoxButtons.OK, MessageBoxIcon.Error); return; // muss gemacht werden, da andernfalls das Ergebnis ausgegeben wird! } } MessageBox.Show("Ergebnis: " + iZahlErgebnis, "Ergebnis", MessageBoxButtons.OK, MessageBoxIcon.Information); } else MessageBox.Show("Die Zahl 2 ist keine gültige Zahl!", "Zahl ungültig", MessageBoxButtons.OK, MessageBoxIcon.Error); } else MessageBox.Show("Die Zahl 1 ist keine gültige Zahl!", "Zahl ungültig", MessageBoxButtons.OK, MessageBoxIcon.Error); } else // if (radioButtonKomma.Checked) { if (Number.IsNumber(textBoxZahl1.Text, out dZahl1)) { if (Number.IsNumber(textBoxZahl2.Text, out dZahl2)) { if (radioButtonAdd.Checked) dZahlErgebnis = Calculator.Addition(dZahl1, dZahl2); else if (radioButtonSub.Checked) dZahlErgebnis = Calculator.Subtraktion(dZahl1, dZahl2); else if (radioButtonMul.Checked) dZahlErgebnis = Calculator.Multiplikation(dZahl1, dZahl2); else // if (radioButtonDiv.Checked) { if (Number.DivisionErlaubt(dZahl2)) { dZahlErgebnis = Calculator.Division(dZahl1, dZahl2); } else { MessageBox.Show("Die Division ist mit der eingegebenen Zahl nicht möglich!", "Rechenoperation ungültig", MessageBoxButtons.OK, MessageBoxIcon.Error); return; // muss gemacht werden, da andernfalls das Ergebnis ausgegeben wird! } } MessageBox.Show("Ergebnis: " + dZahlErgebnis, "Ergebnis", MessageBoxButtons.OK, MessageBoxIcon.Information); } else MessageBox.Show("Die Zahl 2 ist keine gültige Zahl!", "Zahl ungültig", MessageBoxButtons.OK, MessageBoxIcon.Error); } else MessageBox.Show("Die Zahl 1 ist keine gültige Zahl!", "Zahl ungültig", MessageBoxButtons.OK, MessageBoxIcon.Error); } } } }