Galileo Computing < openbook > Galileo Computing - Professionelle Bücher. Auch für Einsteiger.
Professionelle Bücher. Auch für Einsteiger.

Inhaltsverzeichnis
Über den Autor
Vorwort zur 4. Auflage
1 Allgemeine Einführung in .NET
2 Grundlagen der Sprache C#
3 Klassendesign und Vererbung
4 Weitere .NET-Datentypen
5 Weitere Möglichkeiten von C#
6 Projektmanagement und Visual Studio 2008
7 Fehlerbehandlung und Debugging
8 LINQ
9 Multithreading und asynchrone Methodenaufrufe
10 Arbeiten mit Dateien und Streams
11 Serialisierung
12 Einige wichtige .NET-Klassen
13 Grundlagen zum Erstellen einer Windows-Anwendung
14 Die wichtigsten Steuerelemente
15 Tastatur- und Mausereignisse
16 MDI-Anwendungen
17 Grafische Programmierung mit GDI+
18 Das Drucken (Printing)
19 Steuerelemente entwickeln
20 Programmiertechniken
21 WPF – die Grundlagen
22 Die Layoutcontainer
23 Die WPF-Controls
24 Konzepte von WPF
25 ADO.NET – die Verbindung zu einer Datenbank herstellen
26 Die Datenbankabfrage
27 Der SqlDataAdapter
28 Daten im lokalen Speicher – das DataSet
29 Eine Datenbank aktualisieren
30 Stark typisierte DataSets
31 Weitergabe von Anwendungen
Stichwort

Download:
- ZIP, ca. 13,6 MB
Buch bestellen
Ihre Meinung?

Spacer
<< zurück
Visual C# 2008 von Andreas Kuehnel
Das umfassende Handbuch
Buch: Visual C# 2008

Visual C# 2008
geb., mit DVD
1.366 S., 49,90 Euro
Galileo Computing
ISBN 978-3-8362-1172-7
Pfeil 12 Einige wichtige .NET-Klassen
Pfeil 12.1 Die Klasse »Object«
Pfeil 12.1.1 Der Konstruktor
Pfeil 12.1.2 Die Methoden der Klasse »Object«
Pfeil 12.2 Die Klasse »String«
Pfeil 12.2.1 Das Erzeugen eines Strings
Pfeil 12.2.2 Unveränderliche »String«-Objekte
Pfeil 12.2.3 Die Eigenschaften von »String«
Pfeil 12.2.4 Die Methoden der Klasse »String«
Pfeil 12.2.5 Zusammenfassung der Klasse »String«
Pfeil 12.3 Die Klasse »StringBuilder«
Pfeil 12.3.1 Die Kapazität eines »StringBuilder«-Objekts
Pfeil 12.3.2 Die Konstruktoren der Klasse »StringBuilder«
Pfeil 12.3.3 Die Eigenschaften der Klasse »StringBuilder«
Pfeil 12.3.4 Die Methoden der Klasse »StringBuilder«
Pfeil 12.3.5 Allgemeine Anmerkungen
Pfeil 12.4 Der Typ »DateTime«
Pfeil 12.4.1 Die Zeitspanne »Tick«
Pfeil 12.4.2 Die Konstruktoren von »DateTime«
Pfeil 12.4.3 Die Eigenschaften von »DateTime«
Pfeil 12.4.4 Die Methoden der Klasse »DateTime«
Pfeil 12.4.5 Die Klasse »TimeSpan«
Pfeil 12.5 Die Klasse »Array«
Pfeil 12.5.1 Das Erzeugen eines »Array«-Objekts
Pfeil 12.5.2 Die Eigenschaften eines »Array«-Objekts
Pfeil 12.5.3 Die Methoden der Klasse »Array«
Pfeil 12.5.4 Array-Elemente sortieren
Pfeil 12.6 Ausgabeformatierung
Pfeil 12.6.1 Formatierung mit der Methode »String.Format«
Pfeil 12.6.2 Formatierung mit der Methode »ToString«
Pfeil 12.6.3 Benutzerdefinierte Formatierung

12 Einige wichtige .NET-Klassen


Galileo Computing - Zum Seitenanfang

12.1 Die Klasse »Object« Zur nächsten ÜberschriftZur vorigen Überschrift

Alle Klassen in der Klassenbibliothek des .NET Frameworks sind Mitglieder einer Klassenhierarchie, die sich über viele Verzweigungen in aufgabenspezifische Bereiche gliedert. Alle Klassen, so tief sie auch im Dickicht dieser Hierarchie stecken mögen, lassen sich aber auf die gemeinsame Basisklasse Object zurückführen. Wenn Sie eine benutzerdefinierte Klasse entwickeln, müssen Sie nicht explizit angeben, dass Ihre Klasse von Object abgeleitet ist – diese Ableitung geschieht implizit. Dass sich alle Klassen von Object ableiten, hat eine ganz wesentliche Konsequenz: Jeder Typ des Systems weist ein Minimum gemeinsamer Verhaltensweisen auf.


Galileo Computing - Zum Seitenanfang

12.1.1 Der Konstruktor Zur nächsten ÜberschriftZur vorigen Überschrift

Die Liste der Konstruktoren ist nicht sehr lang – es gibt nur einen, der parameterlos ist und von jeder abgeleiteten Klasse aufgerufen wird, wenn ein Objekt erstellt wird. Wie Sie wissen, erfolgt dieser Aufruf implizit.


Galileo Computing - Zum Seitenanfang

12.1.2 Die Methoden der Klasse »Object« topZur vorigen Überschrift

Insgesamt sieben Methoden vererbt die Klasse Object an ihre Subklassen. Fünf dieser Methoden sind public und damit öffentlich, die beiden anderen Methoden protected und werden daher zwar vererbt, erlauben aber nur den Zugriff aus der erbenden Klasse heraus.

Sehen wir uns zunächst in Tabelle 12.1 alle Methoden in einem Überblick an.


Tabelle 12.1 Die Methoden der Klasse »Object«

Methoden Beschreibung

Equals

Diese Methode vergleicht zwei Objektreferenzen und liefert einen booleschen Wert zurück, dem entnommen werden kann, ob die beiden Referenzen auf dasselbe Objekt zeigen.

Finalize

Dient dazu, Ressourcen der Klasse freizugeben, wenn das Objekt zerstört wird.

GetHashCode

Liefert einen objektspezifischen Identifizierer.

GetType

Liefert die Referenz auf eine Type-Instanz zurück, die den Typ des aktuellen Objekts beschreibt.

MemberwiseClone

Dupliziert die aktuelle Instanz und liefert die Referenz auf das Duplikat zurück.

ReferenceEquals

Vergleicht zwei Objektreferenzen und liefert einen booleschen Wert zurück, dem entnommen werden kann, ob die beiden Referenzen auf dasselbe Objekt zeigen.

ToString

Liefert den vollqualifizierten Namen einer Klasse.


Referenzvergleiche mit »Equals« und »ReferenceEquals«

Die beiden Methoden Equals und ReferenceEquals sind sich per Definition sehr ähnlich. Es werden zwei Objektvariablen miteinander verglichen, um festzustellen, ob beide dasselbe Objekt im Speicher referenzieren:

ClassA firstRef = new ClassA(); 
ClassA secondRef; 
secondRef = firstRef; 
Console.WriteLine(Object.Equals(firstRef, secondRef));

In diesem Codefragment wird die Referenz firstRef der Variablen secondRef zugewiesen. Beide Referenzen zeigen auf dasselbe konkrete Objekt, was der Aufruf der Equals-Methode bestätigt: Es wird true ausgegeben, was als referenzielle Identität der beiden Objektvariablen zu interpretieren ist. In diesem Fall können Sie sogar Equals gegen ReferenceEquals austauschen, am Ergebnis wird sich nichts ändern.

Sehen wir uns die Definition dieser beiden Methoden an, von denen Equals überladen ist:

public virtual bool Equals(object); public static bool Equals(object, object); public static bool ReferenceEquals(object, object);

Die erste Variante der Equals-Methode ist als Instanzmethode, die zweite als Klassenmethode implementiert. Beachten Sie, dass die Instanzmethode als virtual gekennzeichnet ist und von jeder Klasse polymorph überschrieben werden kann. Die statische Equals-Variante ist nicht überschreibbar, ebenso die ähnlich lautende Methode ReferenceEquals. Damit ist auch garantiert, dass das Ergebnis des Aufrufs einer dieser beiden Methoden immer den Vergleich zwischen zwei Objektreferenzen liefert: Es ist true, wenn beide Referenzen auf ein und dasselbe Objekt verweisen, andernfalls lautet das Ergebnis false.

Das Überschreiben von »Equals« und die Methode »GetHashCode«

Wollen Sie selbst die Equals-Methode überschreiben, sollten Sie immer eine wichtige Regel beachten:


Wird die Equals-Methode einer Klasse überschrieben, sollte auch die Methode GetHashCode überschrieben werden.


Schauen wir uns kurz die Definition dieser Methode an:

public virtual int GetHashCode();

Was aber leistet die Methode GetHashCode, und wozu dient sie?

Ein Hashcode ist eine Zahl vom Typ int, die ein bestimmtes Objekt eindeutig identifiziert. Diese Zahl wird auch als Schlüssel (Key) bezeichnet, der immer zusammen mit einem Wert, beispielsweise einer Referenz, in Erscheinung tritt. Das Schlüssel-Wert-Paar wird in einer Hashtabelle verwaltet.

Jedes .NET-Objekt ist durch einen eindeutigen Schlüssel identifizierbar. Was hat das aber mit der Empfehlung zu tun, dass Sie als Entwickler GetHashCode überschreiben sollten, wenn Sie die Methode Equals überschreiben?

Standardmäßig benutzen wir Equals zum Referenzvergleich. Es könnte, wie Sie oben schon gesehen haben, natürlich auch ReferenceEquals sein oder – und genau das ist der entscheidende Punkt – auch über den Hashcode verglichen werden. Das folgende Beispiel beweist das. Es enthält eine Klasse mit einem parametrisierten Konstruktor, dem ein int übergeben wird. In der Main-Prozedur wird sowohl über Equals als auch über GetHashCode ein Vergleich angestellt, um zu bestimmen, ob zwei Variablen dasselbe Objekt referenzieren.

// ---------------------------------------------------------
// Beispiel: ...\Kapitel 12\HashCode
// ------------------------------------------------------------
class Program { 
  static void Main(string[] args) { 
    ClassA obj1 = new ClassA(5); 
    ClassA obj2 = obj1;

    // Vergleich auf Basis des Hashcodes 
    if(obj2.GetHashCode() == obj1.GetHashCode()) 
      Console.WriteLine("Hashcode: Objekte sind gleich");

    // Vergleich auf Basis der Equals-Methode 
    if(obj2.Equals(obj1)) 
      Console.WriteLine("Equals: Objekte sind gleich"); 
    Console.ReadLine(); 
  } 
}

class ClassA { 
  public int MyProp;

  public ClassA(int i) { 
    MyProp = i; 
  } 
}

Die Ausgabe ist wie erwartet: Über beide Methodenaufrufe wird die Gleichheit festgestellt, da mit der Zuweisung der Objektvariablen obj1 an obj2 auch der Hashcode des Objekts obj1 gleichermaßen Berücksichtigung findet – wie alle anderen Felder des Objekts.

Equals vergleicht zwei Referenzen. Dem Überschreiben dieser Methode könnte die Idee zugrunde liegen, andere Vergleichskriterien für den betreffenden Typ heranzuziehen, beispielsweise bestimmte Feldinhalte zu vergleichen. Für eine solche Klasse würde gelten, dass zwei Objektvariablen dieses Typs per Definition dann »gleich« sind, wenn sie sich in den Feldinhalten nicht unterscheiden.

Es könnte beispielsweise festgelegt werden, dass zwei Variablen mit gleichem Feldinhalt grundsätzlich immer dasselbe Objekt referenzieren sollen. Diese Technik, die der Schonung der Speicherressourcen dient, ist nicht neu. String-Objekte werden nach ähnlichen Kriterien erzeugt:

string str1 = "Hallo Welt"; 
string str2 = "Hallo Welt"; 
Console.WriteLine(str1.GetHashCode()); 
Console.WriteLine(str1.GetHashCode());

Beide Zeichenfolgen haben denselben Inhalt, referenzieren dieselbe Adresse im Hauptspeicher und zeigen demnach auf dasselbe konkrete Objekt.

Wir wollen nun die Aussage von Equals so definieren, dass zwei Objekte vom Typ ClassA dann als gleich angesehen werden, wenn ihre Eigenschaft MyProp jeweils denselben Inhalt aufweist. Mit dieser Vorgabe wollen wir die Klasse ClassA unseres Beispiels durch die überschriebene Methode Equals ergänzen:

class ClassA { 
  public int MyProp;

  public ClassA(int i) { 
    MyProp = i; 
  }

  public override bool Equals(object obj) { 
    // Prüfen, ob ein gültiges Objekt übergeben wurde und ob 
    // dieses auch dem Typ der Klasse entspricht 
    if((obj == null) || !(obj is ClassA)) 
      return false; 
    // Rückgabewert des Feldvergleichs 
    return MyProp == ((ClassA)obj).MyProp; 
  } 
  ... 
}

Als Erstes wird in der Methode geprüft, ob ein gültiges Objekt über den Parameter obj an die Methode übergeben wird und ob dieses auch dem Typ ClassA entspricht. Der letzte Vergleich ist notwendig, da der Parameter vom Typ Object ist und damit die Übergabe jedes x-beliebigen Typs erlaubt.

Sind beide Bedingungen erfüllt, kommt es mit

return MyProp == ((ClassA)obj).MyProp;

zu einem Vergleich der beiden Eigenschaften. Sind deren Inhalte identisch, liefert die Vergleichsoperation true zurück. Weichen die Inhalte voneinander ab, ist der Rückgabewert false.

Um die Änderung zu testen, müssen wir nur noch ein wenig am Code in Main ändern. Wir wollen jetzt nicht mehr den Nachweis führen, dass ein konkretes Objekt, das über zwei Referenzen angesprochen werden kann, denselben Hashcode aufweist, sondern das Ziel soll lauten, den Nachweis zu führen, dass mit der Überschreibung der Methode Equals auch die Methode GetHashCode überschrieben werden soll.

static void Main(string[] args) { 
  ClassA obj1 = new ClassA(5); 
  ClassA obj2 = new ClassA(5);

  // Vergleich auf Basis des Hashcodes 
  if(obj2.GetHashCode() == obj1.GetHashCode()) 
    Console.WriteLine("Hashcode: Objekte sind gleich"); 
  else 
    Console.WriteLine("Hashcode: Objekte sind nicht gleich");

  // Vergleich auf Basis der Equals-Methode 
  if(obj2.Equals(obj1)) 
    Console.WriteLine("Equals: Objekte sind gleich"); 
  else 
    Console.WriteLine("Equals: Objekte sind nicht gleich"); 
  Console.ReadLine(); 
}

Der Vergleich mit der Equals-Methode liefert die Aussage, dass beide Objekte gleich sind, aber der Vergleich über den Hashcode schlägt natürlich fehl, weil es sich um zwei verschiedene Objekte handelt.

Und genau in diesem Punkt besteht das Dilemma, wenn Sie zwar Equals, aber nicht GetHashCode überschreiben. Ein Benutzer Ihrer Klasse, der Objekte des Typs ClassA in einer HashTable sammelt, wird vielleicht einen Vergleich anhand des Hashcodes ziehen und nicht mit Equals. Es kommt zu einer widersprüchlichen Aussage, und die Klasse ist inkonsistent.

Es gehört nicht zu den trivialen Aufgaben, einen passenden Algorithmus zur Generierung des Hashcodes zu implementieren, wenn vom Standard abweichende Vergleichskriterien eine Rolle spielen. Es gibt zu diesem Thema einige gute, wenn auch langatmige Abhandlungen. Es wird jedoch immer ein Wert des Objekts zur Generierung des Hashcodes herangezogen – im einfachsten Fall der Inhalt einer Instanzvariablen des Objekts, z. B.:

public class ClassA { 
  int intVar; 
  // weiterer Klassencode 
  public override int GetHashCode() { 
    // mathematische Operation mit intVar 
    // return Hashcode; 
  } 
}

Das komplette Beispiel finden Sie auf der Buch-DVD unter:

...\Kapitel 12\HashCodeOverriding.

»ToString« und »GetType«

Wenden wir uns den beiden nächsten Methoden zu: ToString und GetType. Widmen wir uns zunächst der erstgenannten, die wir in den vergangenen Kapiteln schon oft benutzt haben:

public virtual string ToString();

ToString liefert per Definition eine Zeichenfolge zurück, der den vollqualifizierten Namen der Klasse, also einschließlich der Angabe des Namespace, enthält. Viele Klassen überschreiben diese Methode, die dann einen anderen Rückgabewert hat. Sehen wir uns das an zwei Beispielen an:

string strText = "Visual C# ist spitze!"; 
Console.WriteLine(strText.ToString()); 
int intVar = 4711; 
Console.WriteLine(intVar.ToString());

Die Ausgabe lautet:

Visual C# ist spitze!

und

4711

Die Typen String und int überschreiben demnach ToString und liefern den Inhalt der Variablen, auf der die Methode aufgerufen worden ist.

Mit GetType können Sie sich den Typ der Klasse besorgen, allerdings müssen Sie dazu die Rückgabe in einen String konvertieren, z. B.:

int intVar = 10; 
Console.WriteLine(Convert.ToString(intVar.GetType()));

Jetzt wird nicht der Inhalt der Variablen, sondern der Datentyp ausgegeben. Sie müssen an dieser Stelle eine Konvertierung vornehmen, weil der Rückgabewert vom Typ Type ist:

public Type GetType();

Die Klasse Type liefert eine Referenz auf das Type-Objekt eines konkreten Objekts zurück. Dieses versetzt uns in die Lage, den Datentyp einer genaueren Analyse zu unterziehen.

Die Methode »MemberwiseClone«

Die Methode MemberwiseClone kopiert ein vorhandenes Objekt und liefert die Referenz auf die Kopie.

protected object MemberwiseClone();

Dabei werden alle Felder des Originals dupliziert: Felder, die auf Wertetypen basieren, werden bitweise kopiert, ebenso die auf Referenztypen basierenden Felder. Das bedeutet, dass die in einem Objekt referenzierten Subobjekte ihrerseits nicht dupliziert werden. Sowohl das Originalobjekt als auch die Kopie greifen auf dieselben Subobjekte zu.

MemberwiseClone ist geschützt deklariert und kann nur aus der aktuellen Instanz heraus aufgerufen werden. Sie müssen daher eine öffentliche Methode bereitstellen, auf die externer Code zugreifen kann. Die .NET-Klassenbibliothek bietet dazu mit ICloneable ein Interface an, dessen Sie sich bedienen sollten. Dieses Interface veröffentlicht nur die Methode Clone:

object Clone();

Innerhalb einer zu duplizierenden Klasse wird Clone überschrieben. Clone ruft MemberwiseClone auf das aktuelle Objekt auf und liefert als Rückgabe die Referenz auf das Duplikat:

public object Clone() { 
  return this.MemberwiseClone(); 
}

Etwas komplizierter wird es, wenn in einer Klasse Felder definiert sind, die auf Referenztypen basieren, und Sie gleichzeitig auch alle Subobjekte duplizieren möchten. Schauen Sie sich dazu die Implementierung der Klasse CloneableClass an:

public class CloneableClass : ICloneable { 
  public long MyProp; 
  public ClassA internClass = new ClassA();

  public object Clone() 
    return this.MemberwiseClone(); 
  } 
  ... 
}

Die Methode Clone wird an einen Aufrufer die Referenz auf eine Kopie zurückliefern. In der Kopie wird das Feld MyProp denselben Inhalt aufweisen wie das des Originals. Da MemberwiseClone alle Felder bitweise kopiert, referenziert die Eigenschaft internClass des Duplikats jedoch dasselbe Objekt wie das Original. Benötigen wir auch vom internen Objekt eine Kopie, haben wir zwei Möglichkeiten:

  • Wir erzeugen ein neues Objekt vom Typ ClassA und weisen diesem alle Eigenschaftswerte der Instanz internClass explizit zu.
  • Wir hoffen, dass der Entwickler der Klasse ClassA weitsichtig genug war und die Schnittstelle ICloneable-Methode implementiert.

Wir wollen an einem Beispiel die unter Punkt 2 genannte Variante studieren. Das Objekt dupliziert sich selbst mit MemberwiseClone und liefert die Referenz der Kopie an den Aufrufer zurück. Exemplarisch nehmen wir die folgende Implementierung an:

public class ClassA : ICloneable { 
  public int intVar;

  public ClassA() { 
    Random rand = new Random(); 
    intVar = rand.Next(0, 1000); 
  }

  public object Clone() { 
    return this.MemberwiseClone(); 
  } 
}

Beim Aufruf des parameterlosen Konstruktors wird nach dem Zufallsprinzip eine Zahl zwischen 0 und kleiner 1000 in der Instanzvariablen intVar festgehalten. Sie dient dazu, später den Erfolg des Klonens zu beweisen.

Nun können wir uns noch einmal der Klasse CloneableClass zuwenden und die Methode Clone gemäß unseren Anforderungen überarbeiten.

public class CloneableClass : ICloneable { 
  public long MyProp; 
  private ClassA internClass = new ClassA();

  public object Clone() { 
    CloneableClass internObj; 
    internObj = (CloneableClass)this.MemberwiseClone(); 
    internObj.internClass = (ClassA)this.internClass.Clone(); 
    return internObj; 
  } 
}

Zuerst wird in der Methode Clone die Variable internObj vom Typ CloneableClass deklariert und dieser über MemberwiseClone die Referenz auf das Duplikat zugewiesen:

internObj = (CloneableClass)this.MemberwiseClone();

Der Rückgabewert von MemberwiseClone ist vom Typ Object und muss in den Typ CloneableClass konvertiert werden. Die Kopie referenziert noch dasselbe interne Objekt wie das Original. Vom Objekt internClass besorgen wir uns deshalb eine Kopie und weisen diese dem Feld internClass der Klone zu.

Damit haben wir unser Ziel erreicht. Was uns jetzt noch fehlt, ist die Bestätigung unserer Überlegungen. Dazu benutzen wir die Methode GetHashCode, da sich jedes Objekt durch einen eigenen Hashcode identifizieren lässt.

// ---------------------------------------------------------
// Beispiel: ...\Kapitel 12\MemberwiseClonen
// -------------------------------------------------------------
class Program { 
  static void Main(string[] args) { 
    CloneableClass obj = new CloneableClass(); 
    CloneableClass dupli = (CloneableClass)obj.Clone(); 
    Console.WriteLine("Hashcode(obj) = {0}", obj.GetHashCode()); 
    Console.WriteLine("Hashcode(dupli) = {0}", 
                                           dupli.GetHashCode()); 
    Console.WriteLine("Hashcode(obj.internClass) = {0}", 
                                 obj.internClass.GetHashCode()); 
    Console.WriteLine("Hashcode(dupli.internClass) = 
                          {0}",dupli.internClass.GetHashCode()); 
    Console.WriteLine("intVar(obj) = {0}", obj.internClass.intVar); 
    Console.WriteLine("intVar (dupli) = {0}", dupli.internClass.intVar); 
    Console.ReadLine(); 
  } 
}

Der Testcode könnte an der Konsole zur folgenden Anzeige führen:

Hashcode(obj) = 70 
Hashcode(dupli) = 72 
Hashcode(obj.internClass) = 73 
Hashcode(dupli.internClass) = 74 
internVar(obj) = 768 
internVar(dupli) = 768

Die Hashcodes der Referenzen dupli und obj sind unterschiedlich, ebenso die des enthaltenen Feldes vom Typ ClassA. Daraus kann der Schluss gezogen werden, dass das ClassA-Feld des Originals ebenfalls geklont worden ist.



Ihr Kommentar

Wie hat Ihnen das <openbook> gefallen? Wir freuen uns immer über Ihre freundlichen und kritischen Rückmeldungen.






<< zurück
  Zum Katalog
Zum Katalog: Visual C# 2008






Visual C# 2008
Jetzt bestellen


 Ihre Meinung?
Wie hat Ihnen das <openbook> gefallen?
Ihre Meinung

 Buchtipps
Zum Katalog: Coding for Fun






 Coding for Fun


Zum Katalog: Einstieg in Visual C# 2008






 Einstieg in
 Visual C# 2008


Zum Katalog: Videotraining - Visual C# 2008






 Videotraining -
 Visual C# 2008


Zum Katalog: Fortgeschrittene Programmierung mit Visual C# 2008






 Fortgeschrittene
 Programmierung mit
 Visual C# 2008


Zum Katalog: Windows Presentation Foundation






 Windows Presentation
 Foundation


Zum Katalog: Visual Basic 2008






 Visual Basic 2008


Zum Katalog: Einstieg in XML






 Einstieg in XML


 Shopping
Versandkostenfrei bestellen in Deutschland und Österreich
InfoInfo




Copyright © Galileo Press 2008
Für Ihren privaten Gebrauch dürfen Sie die Online-Version natürlich ausdrucken. Ansonsten unterliegt das <openbook> denselben Bestimmungen, wie die gebundene Ausgabe: Das Werk einschließlich aller seiner Teile ist urheberrechtlich geschützt. Alle Rechte vorbehalten einschließlich der Vervielfältigung, Übersetzung, Mikroverfilmung sowie Einspeicherung und Verarbeitung in elektronischen Systemen.


[Galileo Computing]

Galileo Press, Rheinwerkallee 4, 53227 Bonn, Tel.: 0228.42150.0, Fax 0228.42150.77, info@galileo-press.de