<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
		<id>https://alda.iwr.uni-heidelberg.de/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Alter</id>
		<title>Alda - User contributions [en]</title>
		<link rel="self" type="application/atom+xml" href="https://alda.iwr.uni-heidelberg.de/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Alter"/>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php/Special:Contributions/Alter"/>
		<updated>2026-05-09T04:36:26Z</updated>
		<subtitle>User contributions</subtitle>
		<generator>MediaWiki 1.30.0</generator>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=2160</id>
		<title>Talk:Main Page</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=2160"/>
				<updated>2008-07-07T17:01:18Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: /* Zu Übung 11 */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Änderungsvorschläge ==&lt;br /&gt;
&lt;br /&gt;
=== zum Übungsbetrieb ===&lt;br /&gt;
&lt;br /&gt;
Bitte die Email-Adressen der Tutoren eintragen, so wie es schon für Thomas Gerlach der Fall ist.&lt;br /&gt;
:Ich hatte jetzt nur die von Daniel (Do Gruppe) parat, habe sie mal eingetragen [[Special:Contributions/83.189.36.163|83.189.36.163]] 13:41, 13 April 2008 (UTC)&lt;br /&gt;
&lt;br /&gt;
Die Übungen sind ja auch mal wieder extrem einfach und beanspruchen fast grkeine Zeit... Ich sitze jetzt schon so ziemlich den ganzen Tag der zweiten Aufgabe und keine Ende in sicht... als ob wir sonst keine Uni hätten.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Zu Übungsblatt 2:==&lt;br /&gt;
In-place sortieren bei selection- und quick-sort ist mir ja noch einsichtig - aber bei merge-sort? ist der algorithmus nicht so spezifiziert, dass man eine neue liste/ein neues array aufbaut? oder sollen wir einfach noch ne kapsel-funktion schreiben, und die neu-aufgebaute liste am ende auf die ausgangsliste verweisen lassen; das wäre zwar kein in-place sortieren im eigentlichen sinne, aber anders kann ich es mir gerade nicht vorstellen.&lt;br /&gt;
:Also ich denke eher, dass das ein Fehler in der Aufgabenstellung ist. Quick und Merge in-place ist doch schon ziemlich kontroproduktiv...&lt;br /&gt;
::U. Köthe: In-place war in der Aufgabe nicht so gemeint, dass die Algorithmen intern keinen zusätzlichen Speicher verwenden dürfen, sondern dass das sortierte Array am Ende das unsortierte überschreiben soll.&lt;br /&gt;
&lt;br /&gt;
Vllt. hilft das ja noch jemandem, der mit seinem quick-sort nicht zu Rande kommt: hab die Erfahrung gemacht, dass es keine korrekten Ergebnisse liefert, wenn man die repeat-untils aus der Spezifikation aus der Vorlesung einfach in whiles mit umgekehrter Bedingung macht (also aus repeat...until a[j]&amp;lt;=a[p] etwa while a[j]&amp;gt;a[p]) - python hat zwar keine repeat-untils, aber mit einem while True...und einem den Block abschließenden if a[j]&amp;lt;=a[p]:break kann man das simulieren, und dann kann man einfach die spezifikationen in python eintippen.&lt;br /&gt;
&lt;br /&gt;
== Spam ==&lt;br /&gt;
&lt;br /&gt;
Ich schlage vor einfach mal alle nicht deutsch(sprachig)en IPs zu verbieten, da die Bots wohl aus USA/AU kommen (http://www.who.is/whois-ip/ip-address/208.17.80.5/).&lt;br /&gt;
Ausserdem vorsicht beim reverten, vorhin sind da ein paar Einträge verlorengegangen.&lt;br /&gt;
&lt;br /&gt;
Eine weitere Möglichkeit besteht darin, die Website unter Passwortschutz zu stellen und das Passwort in der Vorlesung bekanntzugeben. Dieses Passwort muss ja kein großes Geheimnis sein, sondern soll nur Bots daran hindern, die Seite zu manipulieren.&lt;br /&gt;
&lt;br /&gt;
Finde ich alles nicht so sinnvoll. Reicht es nicht, dass man sich registrieren muss? Hat den weiteren Vorteil das man den Autoren mal Namen zuordnen kann... [[User:Thorben|Thorben]]&lt;br /&gt;
&lt;br /&gt;
== Zu Übung 11 ==&lt;br /&gt;
&lt;br /&gt;
Bevor man in gnuplot Kreise zeichnen kann muss der Befehl: &amp;quot;set parametric&amp;quot; ausgeführt werden. Solche Sahcen sind einfach nur extrem zeitraubend...--[[Special:Contributions/84.57.250.56|84.57.250.56]] 17:29, 5 July 2008 (UTC)&lt;br /&gt;
&lt;br /&gt;
Gibt es einen überschaubaren Weg, um den Mittelpunkt eines Dreieckumkreises zu berechnen? Das beschäftigt mich schon sehr lange, obwohl es doch eigentlich nur ein Detail sein sollte. Geometrisch ist es ja recht einfach über die Mittelsenkrechten, aber wie man aus den Koordinaten der Eckpunkte dazu kommt, wird mir genausowenig klar wie das ähnliche Problem bei der Koch-Schneeflocke.&lt;br /&gt;
&lt;br /&gt;
:Die ganze Aufgabe besteht aus solchen Details die sie nicht schwerer machen, aber sie einfach unglaublich viel Zeit braucht. Mit Zerkel und Lineal vielleicht einfach... Um den Mittelpunkt des Umkreises aus zwei Mittelsenkrechten zu berechnen musst du deren Gleichungen gleichsetzen (Die Koordinaten des Schnittpunkts sind ja für beide Linien genau gleich), also z.B.:&lt;br /&gt;
&lt;br /&gt;
 m1: y = 2x + 3&lt;br /&gt;
 m2: y = -0,5x + 1&lt;br /&gt;
&lt;br /&gt;
 2x + 3 = -0,5x + 1&lt;br /&gt;
 2,5x = -2&lt;br /&gt;
 x = -2/1,5&lt;br /&gt;
&lt;br /&gt;
:Diese Gleichung kann in Python einfach berechnet werden (da sie ja immer die gleiche Form hat...) wenn du m (also die Steigung) und b (also den y-Achsenabschnitt) der Mittelsenkrechten kennst, also etwa:&lt;br /&gt;
&lt;br /&gt;
 x = (m2.bisector.b - m1.bisector.b) / (m1.bisector.m - m2.bisector.m)&lt;br /&gt;
&lt;br /&gt;
:Dann setzt du das x in eine der Gleichungen ein, und hast somit den Schnittpunkt gefunden.--[[User:Alter|Alter]] 17:01, 7 July 2008 (UTC)&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=1115</id>
		<title>Talk:Main Page</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=1115"/>
				<updated>2008-05-19T19:31:45Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Änderungsvorschläge ==&lt;br /&gt;
&lt;br /&gt;
=== zum Übungsbetrieb ===&lt;br /&gt;
&lt;br /&gt;
Bitte die Email-Adressen der Tutoren eintragen, so wie es schon für Thomas Gerlach der Fall ist.&lt;br /&gt;
:Ich hatte jetzt nur die von Daniel (Do Gruppe) parat, habe sie mal eingetragen [[Special:Contributions/83.189.36.163|83.189.36.163]] 13:41, 13 April 2008 (UTC)&lt;br /&gt;
&lt;br /&gt;
Die Übungen sind ja auch mal wieder extrem einfach und beanspruchen fast grkeine Zeit... Ich sitze jetzt schon so ziemlich den ganzen Tag der zweiten Aufgabe und keine Ende in sicht... als ob wir sonst keine Uni hätten.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Zu Übungsblatt 2:==&lt;br /&gt;
In-place sortieren bei selection- und quick-sort ist mir ja noch einsichtig - aber bei merge-sort? ist der algorithmus nicht so spezifiziert, dass man eine neue liste/ein neues array aufbaut? oder sollen wir einfach noch ne kapsel-funktion schreiben, und die neu-aufgebaute liste am ende auf die ausgangsliste verweisen lassen; das wäre zwar kein in-place sortieren im eigentlichen sinne, aber anders kann ich es mir gerade nicht vorstellen.&lt;br /&gt;
:Also ich denke eher, dass das ein Fehler in der Aufgabenstellung ist. Quick und Merge in-place ist doch schon ziemlich kontroproduktiv...&lt;br /&gt;
::U. Köthe: In-place war in der Aufgabe nicht so gemeint, dass die Algorithmen intern keinen zusätzlichen Speicher verwenden dürfen, sondern dass das sortierte Array am Ende das unsortierte überschreiben soll.&lt;br /&gt;
&lt;br /&gt;
Vllt. hilft das ja noch jemandem, der mit seinem quick-sort nicht zu Rande kommt: hab die Erfahrung gemacht, dass es keine korrekten Ergebnisse liefert, wenn man die repeat-untils aus der Spezifikation aus der Vorlesung einfach in whiles mit umgekehrter Bedingung macht (also aus repeat...until a[j]&amp;lt;=a[p] etwa while a[j]&amp;gt;a[p]) - python hat zwar keine repeat-untils, aber mit einem while True...und einem den Block abschließenden if a[j]&amp;lt;=a[p]:break kann man das simulieren, und dann kann man einfach die spezifikationen in python eintippen.&lt;br /&gt;
&lt;br /&gt;
== Spam ==&lt;br /&gt;
&lt;br /&gt;
Ich schlage vor einfach mal alle nicht deutsch(sprachig)en IPs zu verbieten, da die Bots wohl aus USA/AU kommen (http://www.who.is/whois-ip/ip-address/208.17.80.5/).&lt;br /&gt;
Ausserdem vorsicht beim reverten, vorhin sind da ein paar Einträge verlorengegangen.&lt;br /&gt;
&lt;br /&gt;
Eine weitere Möglichkeit besteht darin, die Website unter Passwortschutz zu stellen und das Passwort in der Vorlesung bekanntzugeben. Dieses Passwort muss ja kein großes Geheimnis sein, sondern soll nur Bots daran hindern, die Seite zu manipulieren.&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=1006</id>
		<title>Talk:Main Page</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=1006"/>
				<updated>2008-05-16T14:59:02Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Änderungsvorschläge ==&lt;br /&gt;
&lt;br /&gt;
=== zum Übungsbetrieb ===&lt;br /&gt;
&lt;br /&gt;
Bitte die Email-Adressen der Tutoren eintragen, so wie es schon für Thomas Gerlach der Fall ist.&lt;br /&gt;
:Ich hatte jetzt nur die von Daniel (Do Gruppe) parat, habe sie mal eingetragen [[Special:Contributions/83.189.36.163|83.189.36.163]] 13:41, 13 April 2008 (UTC)&lt;br /&gt;
&lt;br /&gt;
Die Übungen sind ja auch mal wieder extrem einfach und beanspruchen fast grkeine Zeit... Ich sitze jetzt schon so ziemlich den ganzen Tag der zweiten Aufgabe und keine Ende in sicht... als ob wir sonst keine Uni hätten.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Zu Übungsblatt 2:==&lt;br /&gt;
In-place sortieren bei selection- und quick-sort ist mir ja noch einsichtig - aber bei merge-sort? ist der algorithmus nicht so spezifiziert, dass man eine neue liste/ein neues array aufbaut? oder sollen wir einfach noch ne kapsel-funktion schreiben, und die neu-aufgebaute liste am ende auf die ausgangsliste verweisen lassen; das wäre zwar kein in-place sortieren im eigentlichen sinne, aber anders kann ich es mir gerade nicht vorstellen.&lt;br /&gt;
:Also ich denke eher, dass das ein Fehler in der Aufgabenstellung ist. Quick und Merge in-place ist doch schon ziemlich kontroproduktiv...&lt;br /&gt;
::U. Köthe: In-place war in der Aufgabe nicht so gemeint, dass die Algorithmen intern keinen zusätzlichen Speicher verwenden dürfen, sondern dass das sortierte Array am Ende das unsortierte überschreiben soll.&lt;br /&gt;
&lt;br /&gt;
Vllt. hilft das ja noch jemandem, der mit seinem quick-sort nicht zu Rande kommt: hab die Erfahrung gemacht, dass es keine korrekten Ergebnisse liefert, wenn man die repeat-untils aus der Spezifikation aus der Vorlesung einfach in whiles mit umgekehrter Bedingung macht (also aus repeat...until a[j]&amp;lt;=a[p] etwa while a[j]&amp;gt;a[p]) - python hat zwar keine repeat-untils, aber mit einem while True...und einem den Block abschließenden if a[j]&amp;lt;=a[p]:break kann man das simulieren, und dann kann man einfach die spezifikationen in python eintippen.&lt;br /&gt;
&lt;br /&gt;
== Spam ==&lt;br /&gt;
&lt;br /&gt;
Ich schlage vor einfach mal alle nicht deutsch(sprachig)en IPs zu verbieten, da die Bots wohl aus USA/AU kommen (http://www.who.is/whois-ip/ip-address/208.17.80.5/).&lt;br /&gt;
Ausserdem vorsicht beim reverten, vorhin sind da ein paar Einträge verlorengegangen.&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=846</id>
		<title>Talk:Main Page</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=846"/>
				<updated>2008-05-13T18:19:42Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Änderungsvorschläge ==&lt;br /&gt;
&lt;br /&gt;
=== zum Übungsbetrieb ===&lt;br /&gt;
&lt;br /&gt;
Bitte die Email-Adressen der Tutoren eintragen, so wie es schon für Thomas Gerlach der Fall ist.&lt;br /&gt;
:Ich hatte jetzt nur die von Daniel (Do Gruppe) parat, habe sie mal eingetragen [[Special:Contributions/83.189.36.163|83.189.36.163]] 13:41, 13 April 2008 (UTC)&lt;br /&gt;
&lt;br /&gt;
Die Übungen sind ja auch mal wieder extrem einfach und beanspruchen fast grkeine Zeit... Ich sitze jetzt schon so ziemlich den ganzen Tag der zweiten Aufgabe und keine Ende in sicht... als ob wir sonst keine Uni hätten.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Zu Übungsblatt 2:==&lt;br /&gt;
In-place sortieren bei selection- und quick-sort ist mir ja noch einsichtig - aber bei merge-sort? ist der algorithmus nicht so spezifiziert, dass man eine neue liste/ein neues array aufbaut? oder sollen wir einfach noch ne kapsel-funktion schreiben, und die neu-aufgebaute liste am ende auf die ausgangsliste verweisen lassen; das wäre zwar kein in-place sortieren im eigentlichen sinne, aber anders kann ich es mir gerade nicht vorstellen.&lt;br /&gt;
:Also ich denke eher, dass das ein Fehler in der Aufgabenstellung ist. Quick und Merge in-place ist doch schon ziemlich kontroproduktiv...&lt;br /&gt;
::U. Köthe: In-place war in der Aufgabe nicht so gemeint, dass die Algorithmen intern keinen zusätzlichen Speicher verwenden dürfen, sondern dass das sortierte Array am Ende das unsortierte überschreiben soll.&lt;br /&gt;
&lt;br /&gt;
Vllt. hilft das ja noch jemandem, der mit seinem quick-sort nicht zu Rande kommt: hab die Erfahrung gemacht, dass es keine korrekten Ergebnisse liefert, wenn man die repeat-untils aus der Spezifikation aus der Vorlesung einfach in whiles mit umgekehrter Bedingung macht (also aus repeat...until a[j]&amp;lt;=a[p] etwa while a[j]&amp;gt;a[p]) - python hat zwar keine repeat-untils, aber mit einem while True...und einem den Block abschließenden if a[j]&amp;lt;=a[p]:break kann man das simulieren, und dann kann man einfach die spezifikationen in python eintippen.&lt;br /&gt;
&lt;br /&gt;
== Spam ==&lt;br /&gt;
&lt;br /&gt;
Ich schlage vor einfach mal alle nicht deutsch(sprachig)en IPs zu verbieten, da die Bots wohl aus USA/AU kommen (http://www.who.is/whois-ip/ip-address/208.17.80.5/).&lt;br /&gt;
Ausserdem vorsicht beim reverten, vorhin sind da ein paar Einträge verlorengegangen.&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Effizienz&amp;diff=749</id>
		<title>Talk:Effizienz</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Effizienz&amp;diff=749"/>
				<updated>2008-05-12T13:52:29Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: Weiterführende Links&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Weiterführende Links ==&lt;br /&gt;
&lt;br /&gt;
* Deutsche Wikipedia: http://de.wikipedia.org/wiki/Landau-Symbole&lt;br /&gt;
* linux-related.de: http://www.linux-related.de/index.html?/coding/o-notation.htm&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=743</id>
		<title>Talk:Main Page</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=743"/>
				<updated>2008-05-12T13:40:17Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: Undo revision 742 by 61.155.41.165 (Talk)&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Änderungsvorschläge ==&lt;br /&gt;
&lt;br /&gt;
=== zum Übungsbetrieb ===&lt;br /&gt;
&lt;br /&gt;
Bitte die Email-Adressen der Tutoren eintragen, so wie es schon für Thomas Gerlach der Fall ist.&lt;br /&gt;
:Ich hatte jetzt nur die von Daniel (Do Gruppe) parat, habe sie mal eingetragen [[Special:Contributions/83.189.36.163|83.189.36.163]] 13:41, 13 April 2008 (UTC)&lt;br /&gt;
&lt;br /&gt;
Die Übungen sind ja auch mal wieder extrem einfach und beanspruchen fast grkeine Zeit... Ich sitze jetzt schon so ziemlich den ganzen Tag der zweiten Aufgabe und keine Ende in sicht... als ob wir sonst keine Uni hätten.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Zu Übungsblatt 2:==&lt;br /&gt;
In-place sortieren bei selection- und quick-sort ist mir ja noch einsichtig - aber bei merge-sort? ist der algorithmus nicht so spezifiziert, dass man eine neue liste/ein neues array aufbaut? oder sollen wir einfach noch ne kapsel-funktion schreiben, und die neu-aufgebaute liste am ende auf die ausgangsliste verweisen lassen; das wäre zwar kein in-place sortieren im eigentlichen sinne, aber anders kann ich es mir gerade nicht vorstellen.&lt;br /&gt;
:Also ich denke eher, dass das ein Fehler in der Aufgabenstellung ist. Quick und Merge in-place ist doch schon ziemlich kontroproduktiv...&lt;br /&gt;
::U. Köthe: In-place war in der Aufgabe nicht so gemeint, dass die Algorithmen intern keinen zusätzlichen Speicher verwenden dürfen, sondern dass das sortierte Array am Ende das unsortierte überschreiben soll.&lt;br /&gt;
&lt;br /&gt;
Vllt. hilft das ja noch jemandem, der mit seinem quick-sort nicht zu Rande kommt: hab die Erfahrung gemacht, dass es keine korrekten Ergebnisse liefert, wenn man die repeat-untils aus der Spezifikation aus der Vorlesung einfach in whiles mit umgekehrter Bedingung macht (also aus repeat...until a[j]&amp;lt;=a[p] etwa while a[j]&amp;gt;a[p]) - python hat zwar keine repeat-untils, aber mit einem while True...und einem den Block abschließenden if a[j]&amp;lt;=a[p]:break kann man das simulieren, und dann kann man einfach die spezifikationen in python eintippen.&lt;br /&gt;
&lt;br /&gt;
== Spam ==&lt;br /&gt;
&lt;br /&gt;
Ich schlage vor einfach mal alle nicht deutsch(sprachig)en IPs zu verbieten, da die Bots wohl aus USA/AU kommen (http://www.who.is/whois-ip/ip-address/208.17.80.5/).&lt;br /&gt;
Ausserdem vorsicht beim reverten, vorhin sind da ein paar Einträge verlorengegangen.&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=725</id>
		<title>Talk:Main Page</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=725"/>
				<updated>2008-05-12T10:43:06Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Änderungsvorschläge ==&lt;br /&gt;
&lt;br /&gt;
=== zum Übungsbetrieb ===&lt;br /&gt;
&lt;br /&gt;
Bitte die Email-Adressen der Tutoren eintragen, so wie es schon für Thomas Gerlach der Fall ist.&lt;br /&gt;
:Ich hatte jetzt nur die von Daniel (Do Gruppe) parat, habe sie mal eingetragen [[Special:Contributions/83.189.36.163|83.189.36.163]] 13:41, 13 April 2008 (UTC)&lt;br /&gt;
&lt;br /&gt;
Die Übungen sind ja auch mal wieder extrem einfach und beanspruchen fast grkeine Zeit... Ich sitze jetzt schon so ziemlich den ganzen Tag der zweiten Aufgabe und keine Ende in sicht... als ob wir sonst keine Uni hätten.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Zu Übungsblatt 2:==&lt;br /&gt;
In-place sortieren bei selection- und quick-sort ist mir ja noch einsichtig - aber bei merge-sort? ist der algorithmus nicht so spezifiziert, dass man eine neue liste/ein neues array aufbaut? oder sollen wir einfach noch ne kapsel-funktion schreiben, und die neu-aufgebaute liste am ende auf die ausgangsliste verweisen lassen; das wäre zwar kein in-place sortieren im eigentlichen sinne, aber anders kann ich es mir gerade nicht vorstellen.&lt;br /&gt;
:Also ich denke eher, dass das ein Fehler in der Aufgabenstellung ist. Quick und Merge in-place ist doch schon ziemlich kontroproduktiv...&lt;br /&gt;
::U. Köthe: In-place war in der Aufgabe nicht so gemeint, dass die Algorithmen intern keinen zusätzlichen Speicher verwenden dürfen, sondern dass das sortierte Array am Ende das unsortierte überschreiben soll.&lt;br /&gt;
&lt;br /&gt;
Vllt. hilft das ja noch jemandem, der mit seinem quick-sort nicht zu Rande kommt: hab die Erfahrung gemacht, dass es keine korrekten Ergebnisse liefert, wenn man die repeat-untils aus der Spezifikation aus der Vorlesung einfach in whiles mit umgekehrter Bedingung macht (also aus repeat...until a[j]&amp;lt;=a[p] etwa while a[j]&amp;gt;a[p]) - python hat zwar keine repeat-untils, aber mit einem while True...und einem den Block abschließenden if a[j]&amp;lt;=a[p]:break kann man das simulieren, und dann kann man einfach die spezifikationen in python eintippen.&lt;br /&gt;
&lt;br /&gt;
== Spam ==&lt;br /&gt;
&lt;br /&gt;
Ich schlage vor einfach mal alle nicht deutsch(sprachig)en IPs zu verbieten, da die Bots wohl aus USA/AU kommen (http://www.who.is/whois-ip/ip-address/208.17.80.5/).&lt;br /&gt;
Ausserdem vorsicht beim reverten, vorhin sind da ein paar Einträge verlorengegangen.&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=644</id>
		<title>Talk:Main Page</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=644"/>
				<updated>2008-05-11T11:53:08Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Änderungsvorschläge ==&lt;br /&gt;
&lt;br /&gt;
=== zum Übungsbetrieb ===&lt;br /&gt;
&lt;br /&gt;
Bitte die Email-Adressen der Tutoren eintragen, so wie es schon für Thomas Gerlach der Fall ist.&lt;br /&gt;
:Ich hatte jetzt nur die von Daniel (Do Gruppe) parat, habe sie mal eingetragen [[Special:Contributions/83.189.36.163|83.189.36.163]] 13:41, 13 April 2008 (UTC)&lt;br /&gt;
&lt;br /&gt;
Die Übungen sind ja auch mal wieder extrem einfach und beanspruchen fast grkeine Zeit... Ich sitze jetzt schon so ziemlich den ganzen Tag der zweiten Aufgabe und keine Ende in sicht... als ob wir sonst keine Uni hätten.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Zu Übungsblatt 2:==&lt;br /&gt;
In-place sortieren bei selection- und quick-sort ist mir ja noch einsichtig - aber bei merge-sort? ist der algorithmus nicht so spezifiziert, dass man eine neue liste/ein neues array aufbaut? oder sollen wir einfach noch ne kapsel-funktion schreiben, und die neu-aufgebaute liste am ende auf die ausgangsliste verweisen lassen; das wäre zwar kein in-place sortieren im eigentlichen sinne, aber anders kann ich es mir gerade nicht vorstellen.&lt;br /&gt;
:Also ich denke eher, dass das ein Fehler in der Aufgabenstellung ist. Quick und Merge in-place ist doch schon ziemlich kontroproduktiv...&lt;br /&gt;
::U. Köthe: In-place war in der Aufgabe nicht so gemeint, dass die Algorithmen intern keinen zusätzlichen Speicher verwenden dürfen, sondern dass das sortierte Array am Ende das unsortierte überschreiben soll.&lt;br /&gt;
&lt;br /&gt;
Vllt. hilft das ja noch jemandem, der mit seinem quick-sort nicht zu Rande kommt: hab die Erfahrung gemacht, dass es keine korrekten Ergebnisse liefert, wenn man die repeat-untils aus der Spezifikation aus der Vorlesung einfach in whiles mit umgekehrter Bedingung macht (also aus repeat...until a[j]&amp;lt;=a[p] etwa while a[j]&amp;gt;a[p]) - python hat zwar keine repeat-untils, aber mit einem while True...und einem den Block abschließenden if a[j]&amp;lt;=a[p]:break kann man das simulieren, und dann kann man einfach die spezifikationen in python eintippen.&lt;br /&gt;
&lt;br /&gt;
== Spam ==&lt;br /&gt;
&lt;br /&gt;
Ich schlage vor einfach mal alle nicht deutsch(sprachig)en IPs zu verbieten, da die Bots wohl aus USA/AU kommen (http://www.who.is/whois-ip/ip-address/208.17.80.5/).&lt;br /&gt;
Ausserdem vorsicht beim reverten, vorhin sind da ein paar Einträge verlorengegangen.&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Effizienz&amp;diff=640</id>
		<title>Effizienz</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Effizienz&amp;diff=640"/>
				<updated>2008-05-10T10:30:46Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;(Vorlesung 7.5.:)&lt;br /&gt;
&lt;br /&gt;
== Laufzeit ==&lt;br /&gt;
Die Laufzeit ist für den Benutzer ein wichtiges Kriterium.&lt;br /&gt;
Schwierigkeit bei der Bestimmung: Die Laufzeit hängt von vielen Faktoren ab die evtl. nicht kontrollierbar sind:&lt;br /&gt;
* Prozessor/Auslastung des Systems&lt;br /&gt;
* Speicher/Cache/Bus&lt;br /&gt;
* Compiler/Optimierer des Compilers (Compiler auf verschiedene Architekturen optimiert?)&lt;br /&gt;
* Geschick des Programmierers&lt;br /&gt;
* Daten (Beispiel Quicksort: Best case und worst case[Vorsortierter Input] stark unterschiedlich)&lt;br /&gt;
All diese Faktoren sind untereinander abhängig.&lt;br /&gt;
&lt;br /&gt;
Laufzeitvergleiche sind mit Vorsicht zu interpretieren.&lt;br /&gt;
Generell sollten bei Vergleichen möglichst wenige Parameter verändert werden, z.B.&lt;br /&gt;
* gleiches Programm(gleiche Kompilierung), gleiche Daten, andere Prozessoren&lt;br /&gt;
oder&lt;br /&gt;
*gleiche CPU, Daten, andere Programme (Vergleich von Algorithmen)&lt;br /&gt;
&lt;br /&gt;
Beobachtung: Durch Laufzeitmessung ist schwer festzustellen, ob ein Alg prinzipiell besser ist als ein anderer.&lt;br /&gt;
&lt;br /&gt;
== Komplexität ==&lt;br /&gt;
Komplexitätsbetrachtungen ermöglichen den Vergleich der prinzipiellen Eigenschaften von Algorithmen unabhängig von einer Implementation, Umgebung etc.&lt;br /&gt;
      &lt;br /&gt;
Eine einfache Möglichkeit ist das Zählen der Aufrufe einer Schlüsseloperation. Beispiel Sortieren:&lt;br /&gt;
* Anzahl der Vergleiche&lt;br /&gt;
* Anzahl der Vertauschungen&lt;br /&gt;
&lt;br /&gt;
=== Beispiel: Selection Sort ===&lt;br /&gt;
&lt;br /&gt;
  for i in range(len(a)-1):&lt;br /&gt;
    max = i&lt;br /&gt;
    for j in range(i+1, len(a)):&lt;br /&gt;
      if a[j] &amp;lt; a[max]:&lt;br /&gt;
        max = j&lt;br /&gt;
    a[max], a[i] = a[i], a[max]      # swap&lt;br /&gt;
&lt;br /&gt;
*Anzahl der Vergleiche: Ein Vergleich in jedem Durchlauf der inneren Schleife. Es ergibt sich folgende Komplexität:&lt;br /&gt;
*:Ingesamt &amp;lt;math&amp;gt;\sum_{i=0}^{N-2} \sum_{j=i+1}^{N-1}1 = \frac{N}{2} (N-1) \!&amp;lt;/math&amp;gt; Vergleiche.&lt;br /&gt;
&lt;br /&gt;
*Anzahl der Vertauschungen: Eine Vertauschung pro Durchlauf der äußeren Schleife:&lt;br /&gt;
*:Insgesamt &amp;lt;math&amp;gt;N-1 \!&amp;lt;/math&amp;gt; Vertauschungen&lt;br /&gt;
&lt;br /&gt;
Die Komplexität wird durch die Operationen bestimmt, die am häufigsten ausgeführt werden, hier also die Anzahl der Vergleiche. Die Anzahl der Vertauschungen ist kein geeignetes Kriterium für die Komplexität von selection sort, weil der Aufwand in der inneren Schleife ignoriert wird.&lt;br /&gt;
&lt;br /&gt;
=== Fallunterscheidung: Worst und Average Case ===&lt;br /&gt;
&lt;br /&gt;
Die Komplexität ist in der Regel eine Funktion der Eingabegröße (Anzahl der Eingabebits, Anzahl der Eingabeelemente). Sie kann aber auch von der Art der Daten abhängen, nicht nur von der Menge, z.B. vorsortierte Daten bei Quicksort. Um von der Art der Daten unabhängig zu werden, kann man zwei Fälle der Komplexität unterscheiden:&lt;br /&gt;
      &lt;br /&gt;
* Komplexität im ungünstigsten Fall &lt;br /&gt;
*: Der ungünstigste Fall ist die Eingabe gegebener Länge, für die der Algorithmus am langsamsten ist. Der Nachteil dieser Methode besteht darin, dass dieser ungünstige Fall in der Praxis vielleicht gar nicht oder nur selten vorkommt, so dass sich der Algorithmus in Wirklichkeit besser verhält als man nach dieser Analyse erwarten würde. Beim Quicksort-Algorithmus mit zufälliger Wahl des Pivot-Elements müsste z.B. stets das kleinste oder größte Element des aktuellen Intervalls als Pivot-Element gewählt werden, was äußerst unwahrscheinlich ist.&lt;br /&gt;
* Komplexität im durchschnittlichen/typischen Fall&lt;br /&gt;
*: Der typische Fall ist die mittlere Komplexität des Algorithmus über alle möglichen Eingaben. Dazu muss man die Wahrscheinlichkeit jeder möglichen Eingabe kennen, und berechnet dann die mittlere Laufzeit über dieser Wahrscheinlichleitsverteilung. Leider ist die Wahrscheinlichkeit der Eingaben oft nicht bekannt, so dass man geeignete Annahmen treffen muss. Bei Sortieralgorithmen können z.B. alle möglichen Permutationen des Eingabearrays als gleich wahrscheinlich angenommen werden, und der typische Fall ist dann die mittlere Komplexität über alle diese Eingaben. Oft hat man jedoch in der Praxis andere Wahrscheinlichkeitsverteilungen, z.B. sind die Daten oft &amp;quot;fast sortiert&amp;quot; (nur wenige Elemente sind an der falschen Stelle). Dann verhält sich der Algorithmus ebenfalls anders als vorhergesagt.&lt;br /&gt;
&lt;br /&gt;
Wir beschränken uns in dieser Vorlesung auf die Komplexität im ungünstigseten Fall. '''Exakte''' Formeln für Komplexität sind aber auch dann schwer zu gewinnen, wie das folgende Beispiel zeigt:&lt;br /&gt;
&lt;br /&gt;
=== Beispiele aus den Übungen (Gemessene Laufzeiten für Mergesort/Selectionsort) ===&lt;br /&gt;
&lt;br /&gt;
* Mergesort: &amp;lt;math&amp;gt;\frac{0,977N\log N}{\log 2} + 0,267N-4.39 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
*: andere Lösung: &amp;lt;math&amp;gt;1140 N\log(N) - 1819N + 6413 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
* Selectionsort: &amp;lt;math&amp;gt;\frac{1}{2}N^2 - \frac{1}{2N} - 10^{-12} \!&amp;lt;/math&amp;gt;&lt;br /&gt;
*: andere Lösung: &amp;lt;math&amp;gt;1275N^2 - 116003^N + 11111144 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Aus diesen Formeln wird nicht offensichtlich, welcher Algorithmus besser ist.&lt;br /&gt;
Näherung: Betrachte nur '''sehr große Eingaben''' (Meist sind alle Algorithmen schnell genug für kleine Eingaben). Dieses Vorgehen wird als '''Asymptotische Komplexität''' bezeichnet (N gegen unendlich).&lt;br /&gt;
&lt;br /&gt;
=== Asymptotische Komplexität am Beispiel Polynom ===&lt;br /&gt;
&lt;br /&gt;
Polynom: &amp;lt;math&amp;gt;ax^2+bx+c=p\!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;math&amp;gt;x \!&amp;lt;/math&amp;gt; sei die Eingabegröße, und wir betrachten die Entwicklung von &amp;lt;math&amp;gt;p \!&amp;lt;/math&amp;gt; in Abhängigkeit von &amp;lt;math&amp;gt;x \!&amp;lt;/math&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
* &amp;lt;math&amp;gt;x=0 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
*: &amp;lt;math&amp;gt;p=c \!&amp;lt;/math&amp;gt;&lt;br /&gt;
* &amp;lt;math&amp;gt;x=1 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
*: &amp;lt;math&amp;gt;p=a+b+c \!&amp;lt;/math&amp;gt;&lt;br /&gt;
* &amp;lt;math&amp;gt;x=1000 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
*: &amp;lt;math&amp;gt;p=1000000a+1000b+c \approx 1000000a\!&amp;lt;/math&amp;gt;&lt;br /&gt;
* &amp;lt;math&amp;gt;x \to \infty \!&amp;lt;/math&amp;gt;&lt;br /&gt;
*: &amp;lt;math&amp;gt;p \approx x^2a\!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Für sehr große Eingaben verlieren also b und c immer mehr an Bedeutung, so dass am Ende nur noch a für die Komplexitätsbetrachtung wichtig ist.&lt;br /&gt;
&lt;br /&gt;
== O-Notation ==&lt;br /&gt;
* Intuitiv: Für große N dominieren die am schnellsten wachsenden Terme.&lt;br /&gt;
* Formale Definition: &lt;br /&gt;
*: Asymptotische Komplexität: Für zwei Funktionen f(x) und g(x) definiert man &lt;br /&gt;
*::&amp;lt;math&amp;gt;f(x) \in \mathcal{O}(g(x))&amp;lt;/math&amp;gt;&lt;br /&gt;
*:(sprich &amp;quot;f ist in \mathcal{O}(g)&amp;quot; oder &amp;quot;f ist von derselben Größenordnung wie g&amp;quot;) genau dann wenn es eine Konstante &amp;lt;math&amp;gt;c&amp;lt;/math&amp;gt; und ein Argument &amp;lt;math&amp;gt;x_0&amp;lt;/math&amp;gt; gibt, so dass &lt;br /&gt;
*::&amp;lt;math&amp;gt;\forall x &amp;gt; x_0:\quad f(x) \le c g(x)&amp;lt;/math&amp;gt;.&lt;br /&gt;
*:Die Idee hinter dieser Definition ist, dass g(x) eine wesentlich einfachere Funktion ist als f(x), die sich aber nach geeigneter Skalierung (Multiplikation mit c) und für große Argumente x im wesentlichen genauso wie f(x) verhält. Man kann deshalb in der Algorithmenanalyse f(x) durch g(x) ersetzen. &amp;lt;math&amp;gt;f(x) \in \mathcal{O}(g(x))&amp;lt;/math&amp;gt; spielt für Funktionen eine ähnliche Rolle wie der Operator &amp;amp;le; für Zahlen: Falls a &amp;amp;le; b gilt, kann bei einer Abschätzung von oben ebenfalls a durch b ersetzt werden.&lt;br /&gt;
=== Ein einfaches Beispiel ===&lt;br /&gt;
&lt;br /&gt;
[[Image:Sqsqrt.png]]&lt;br /&gt;
&lt;br /&gt;
Rot = &amp;lt;math&amp;gt;x^2 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
Blau = &amp;lt;math&amp;gt;\sqrt{x} \!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;math&amp;gt;\sqrt{x} \in \mathcal{O}(x^2)\!&amp;lt;/math&amp;gt; weil &amp;lt;math&amp;gt;\sqrt{x} \le c x^2\!&amp;lt;/math&amp;gt; für alle &amp;lt;math&amp;gt;x &amp;lt; x_0 = 1 \!&amp;lt;/math&amp;gt; und &amp;lt;math&amp;gt;c = 1\!&amp;lt;/math&amp;gt;, oder auch für &amp;lt;math&amp;gt;x &amp;lt; x_0 = 4 \!&amp;lt;/math&amp;gt; und &amp;lt;math&amp;gt;c = 1/16&amp;lt;/math&amp;gt; (die Wahl von c und x&amp;lt;sub&amp;gt;0&amp;lt;/sub&amp;gt; in der Definition von O(.) ist beliebig, solange die Bedingungen erfüllt sind).&lt;br /&gt;
&lt;br /&gt;
=== Komplexität bei kleinen Eingaben ===&lt;br /&gt;
&lt;br /&gt;
Algorithmus 1: &amp;lt;math&amp;gt;\mathcal{O}(N^2) \!&amp;lt;/math&amp;gt;&lt;br /&gt;
Algortihmus 2: &amp;lt;math&amp;gt;=\mathcal{O}(N\log{N}) \!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Algorithmus 2 ist schneller (Von geringerer Komplexität), aber bei vielen wiederholten kleinen Eingaben ist Algorithmus 1 schneller.&lt;br /&gt;
&lt;br /&gt;
=== Eigenschaften der O-Notation(Rechenregeln) ===&lt;br /&gt;
&lt;br /&gt;
# Transitiv:&lt;br /&gt;
#: &amp;lt;math&amp;gt;f(x) \in \mathcal{O}(g(x)) \land g(x) \in \mathcal{O}(h(x)) \to f(x) \in \mathcal{O}(h(x)) \!&amp;lt;/math&amp;gt;           &lt;br /&gt;
# Additiv:&lt;br /&gt;
#: &amp;lt;math&amp;gt;f(x) \in \mathcal{O}(h(x)) \land g(x) \in \mathcal{O}(h(x)) \to f(x) + g(x) \in \mathcal{O}(h(x)) \!&amp;lt;/math&amp;gt;           &lt;br /&gt;
# Für Monome gilt:&lt;br /&gt;
#: &amp;lt;math&amp;gt;x^k \in \mathcal{O}(x^k)) \land x^k \in \mathcal{O}(x^{k+j}), \forall j \ge 0 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
# Multiplikation mit einer Konstanten:&lt;br /&gt;
#: &amp;lt;math&amp;gt;f(x) \in \mathcal{O}(g(x)) \to cf(x) \in \mathcal{O}(g(x))\!&amp;lt;/math&amp;gt;&lt;br /&gt;
#: andere Schreibweise:&lt;br /&gt;
#: &amp;lt;math&amp;gt;f(x) = cg(x) \to f(x) \in \mathcal{O}(g(x))\!&amp;lt;/math&amp;gt;&lt;br /&gt;
#: Beispiel: &amp;lt;math&amp;gt;ax^2+bx+c \in \mathcal{O}(x^2)\!&amp;lt;/math&amp;gt;&lt;br /&gt;
#: Folgerung für Polynome: &amp;lt;math&amp;gt;a_0+a_1x + ... + a_nx^n \in \mathcal{O}(x^n)\!&amp;lt;/math&amp;gt;&lt;br /&gt;
# Logarithmus:&lt;br /&gt;
#: &amp;lt;math&amp;gt;a, b \neq 1\!&amp;lt;/math&amp;gt;&lt;br /&gt;
#: &amp;lt;math&amp;gt;\log_{a}{x} \in \mathcal{O}(\log_{b}{x})\!&amp;lt;/math&amp;gt;&lt;br /&gt;
#: Die Basis des Logarithmus spielt also keine Rolle.&lt;br /&gt;
#: Beweis hierfür:&lt;br /&gt;
#: &amp;lt;math&amp;gt;\log_{a}{x} = \frac{\log_{b}{x}}{\log_{b}{a}}\!&amp;lt;/math&amp;gt;&lt;br /&gt;
#: &amp;lt;math&amp;gt;c = \log_{b}{a}\!&amp;lt;/math&amp;gt;&lt;br /&gt;
#: &amp;lt;math&amp;gt;c\log_{a}{x} = \log_{b}{x}\!&amp;lt;/math&amp;gt;, wird hier die Regel für Multiplikation mit einer Konstanten angewendet fällt der Konstante Faktor weg.&lt;br /&gt;
#: Insbesondere gilt auch &amp;lt;math&amp;gt;\log_{a}{x} \in \mathcal{O}(\log_{2}{x})\!&amp;lt;/math&amp;gt;, es kann also immer der 2er Logarithmus verewendet werden.&lt;br /&gt;
&lt;br /&gt;
== O-Kalkül ==&lt;br /&gt;
&lt;br /&gt;
# &amp;lt;math&amp;gt;f(x) \in \mathcal{O}(f(x))\!&amp;lt;/math&amp;gt;&lt;br /&gt;
# &amp;lt;math&amp;gt;\mathcal{O}(\mathcal{O}(f(x))) \in \mathcal{O}(f(x))\!&amp;lt;/math&amp;gt;&lt;br /&gt;
# &amp;lt;math&amp;gt;k\mathcal{O}(f(x)) \in \mathcal{O}(f(x))\!&amp;lt;/math&amp;gt;&lt;br /&gt;
# &amp;lt;math&amp;gt;\mathcal{O}(f(x))+c \in \mathcal{O}(f(x))\!&amp;lt;/math&amp;gt;&lt;br /&gt;
# Sequenzregel:&lt;br /&gt;
#: &amp;lt;math&amp;gt;g(x) \in \mathcal{O}(f(x)) \to \mathcal{O}(f(x)) + \mathcal{O}(g(x)) \in \mathcal{O}(f(x))\!&amp;lt;/math&amp;gt;, oder &amp;lt;math&amp;gt;f(x) \in \mathcal{O}(g(x)) \to \mathcal{O}(f(x)) + \mathcal{O}(g(x)) \in \mathcal{O}(g(x))\!&amp;lt;/math&amp;gt;&lt;br /&gt;
#: Informale Schreibweise: &amp;lt;math&amp;gt;\mathcal{O}(max(f(x), (g(x))\!&amp;lt;/math&amp;gt;&lt;br /&gt;
# Aufruf, Verschachtelungsregel:&lt;br /&gt;
#: &amp;lt;math&amp;gt;\mathcal{O}(f(x)) * \mathcal{O}(g(x)) \in \mathcal{O}(f(x) * g(x))\!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== O-Kalkül auf das Beispiel des Selectionsort angewandt ===&lt;br /&gt;
Selectionsort: &amp;lt;math&amp;gt;f(N) = \frac{N^2}{2} - \frac{N}{2} \in \mathcal{O}(\frac{N^2}{2}) \in \mathcal{O}(N^2)\!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Oder via Multiplikationsregel:&lt;br /&gt;
&amp;lt;math&amp;gt;\mathcal{O}(f(x))*\mathcal{O}(g(x)) \in \mathcal{O}(f(x)*g(x))\!&amp;lt;/math&amp;gt;&lt;br /&gt;
: Äußere Schleife: &amp;lt;math&amp;gt;\mathcal{O}f(x)\!&amp;lt;/math&amp;gt;&lt;br /&gt;
:: &amp;lt;math&amp;gt;f(N) = N/2 = \mathcal{O}(N)\!&amp;lt;/math&amp;gt;&lt;br /&gt;
: Innere Schleife: &amp;lt;math&amp;gt;\mathcal{O}g(x)\!&amp;lt;/math&amp;gt;&lt;br /&gt;
:: &amp;lt;math&amp;gt;g(N) = N-2 = \mathcal{O}(N)\!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
:&amp;lt;math&amp;gt;\mathcal{O}(f(N))*\mathcal{O}(g(N)) \in \mathcal{O}(f(x)*g(x))\!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
::&amp;lt;math&amp;gt;\mathcal{O}(N)*\mathcal{O}(N) \in \mathcal{O}(N*N) \in \mathcal{O}(N^2)\!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Nach beiden Vorgehensweisen erreichen wir also den Schluss, dass der Selectionsort die asymptotische Komplexität &amp;lt;math&amp;gt;\mathcal{O}(N^2)\!&amp;lt;/math&amp;gt; besitzt.&lt;br /&gt;
&lt;br /&gt;
=== Zusammenhang zwischen Komplexität und Laufzeit ===&lt;br /&gt;
Wenn ein Rechenschritt 1ms dauert erreichen verschiedene komplexe Algorithmen folgende Leistungen&lt;br /&gt;
&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot; style=&amp;quot;text-align:left&amp;quot;&lt;br /&gt;
|+&lt;br /&gt;
|-&lt;br /&gt;
! Komplexität !! Operationen in 1s !! Operationen in 1min !! Operationen in 1h&lt;br /&gt;
|-&lt;br /&gt;
! &amp;lt;math&amp;gt;\mathcal{O}(N)&amp;lt;/math&amp;gt;&lt;br /&gt;
| 1000 || 60.000 || 3.600.000&lt;br /&gt;
|-&lt;br /&gt;
! &amp;lt;math&amp;gt;\mathcal{O}(n\log{N})&amp;lt;/math&amp;gt;&lt;br /&gt;
| 140 || 4895 || 204094&lt;br /&gt;
|-&lt;br /&gt;
! &amp;lt;math&amp;gt;\mathcal{O}(N^2)&amp;lt;/math&amp;gt;&lt;br /&gt;
| 31 || 244 || 1897&lt;br /&gt;
|-&lt;br /&gt;
! &amp;lt;math&amp;gt;\mathcal{O}(N^3)&amp;lt;/math&amp;gt;&lt;br /&gt;
| 10 || 39 || 153&lt;br /&gt;
|-&lt;br /&gt;
! &amp;lt;math&amp;gt;\mathcal{O}(2^N)&amp;lt;/math&amp;gt;&lt;br /&gt;
| 9 || 15 || 21&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
=== Exponentielle Komplexität ===&lt;br /&gt;
Der letzte Fall (&amp;lt;math&amp;gt;\mathcal{O}(2^N)&amp;lt;/math&amp;gt;) ist von exponentieller Komlexität, das bedeutet eine Verdopplung des Aufwands bewirkt nur, dass die maximale Problemgröße um eine Konstante wächst. Algorithmen mit exponentieller Komplexität heißen '''ineffizient'''.&lt;br /&gt;
&lt;br /&gt;
Dagegen bewirkt bei einer Komplexität von &amp;lt;math&amp;gt;\mathcal{O}(N^3)&amp;lt;/math&amp;gt; ein verdoppelter Aufwand immer noch eine Steigerung der maximalen Problemgörße um den Faktor &amp;lt;math&amp;gt;\sqrt[3]{2}&amp;lt;/math&amp;gt;.&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=639</id>
		<title>Talk:Main Page</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=639"/>
				<updated>2008-05-10T09:22:25Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: Undo revision 638 by 218.104.219.203 (Talk)&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Änderungsvorschläge ==&lt;br /&gt;
&lt;br /&gt;
=== zum Übungsbetrieb ===&lt;br /&gt;
&lt;br /&gt;
Bitte die Email-Adressen der Tutoren eintragen, so wie es schon für Thomas Gerlach der Fall ist.&lt;br /&gt;
:Ich hatte jetzt nur die von Daniel (Do Gruppe) parat, habe sie mal eingetragen [[Special:Contributions/83.189.36.163|83.189.36.163]] 13:41, 13 April 2008 (UTC)&lt;br /&gt;
&lt;br /&gt;
Die Übungen sind ja auch mal wieder extrem einfach und beanspruchen fast grkeine Zeit... Ich sitze jetzt schon so ziemlich den ganzen Tag der zweiten Aufgabe und keine Ende in sicht... als ob wir sonst keine Uni hätten.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Zu Übungsblatt 2:==&lt;br /&gt;
In-place sortieren bei selection- und quick-sort ist mir ja noch einsichtig - aber bei merge-sort? ist der algorithmus nicht so spezifiziert, dass man eine neue liste/ein neues array aufbaut? oder sollen wir einfach noch ne kapsel-funktion schreiben, und die neu-aufgebaute liste am ende auf die ausgangsliste verweisen lassen; das wäre zwar kein in-place sortieren im eigentlichen sinne, aber anders kann ich es mir gerade nicht vorstellen.&lt;br /&gt;
:Also ich denke eher, dass das ein Fehler in der Aufgabenstellung ist. Quick und Merge in-place ist doch schon ziemlich kontroproduktiv...&lt;br /&gt;
::U. Köthe: In-place war in der Aufgabe nicht so gemeint, dass die Algorithmen intern keinen zusätzlichen Speicher verwenden dürfen, sondern dass das sortierte Array am Ende das unsortierte überschreiben soll.&lt;br /&gt;
&lt;br /&gt;
Vllt. hilft das ja noch jemandem, der mit seinem quick-sort nicht zu Rande kommt: hab die Erfahrung gemacht, dass es keine korrekten Ergebnisse liefert, wenn man die repeat-untils aus der Spezifikation aus der Vorlesung einfach in whiles mit umgekehrter Bedingung macht (also aus repeat...until a[j]&amp;lt;=a[p] etwa while a[j]&amp;gt;a[p]) - python hat zwar keine repeat-untils, aber mit einem while True...und einem den Block abschließenden if a[j]&amp;lt;=a[p]:break kann man das simulieren, und dann kann man einfach die spezifikationen in python eintippen.&lt;br /&gt;
&lt;br /&gt;
== Spam ==&lt;br /&gt;
&lt;br /&gt;
Ich schlage vor einfach mal alle nicht deutsch(sprachig)en IPs zu verbieten, da die Bots wohl aus USA/AU kommen (http://www.who.is/whois-ip/ip-address/208.17.80.5/).&lt;br /&gt;
Ausserdem vorsicht beim reverten, vorhin sind da ein paar Einträge verlorengegangen.&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Effizienz&amp;diff=581</id>
		<title>Effizienz</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Effizienz&amp;diff=581"/>
				<updated>2008-05-08T13:08:47Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;(Vorlesung 7.5.:)&lt;br /&gt;
&lt;br /&gt;
== Laufzeit ==&lt;br /&gt;
Die Laufzeit ist für den Benutzer ein wichtiges Kriterium.&lt;br /&gt;
Schwierigkeit bei der Bestimmung: Die Laufzeit hängt von vielen Faktoren ab die evtl. nicht kontrollierbar sind:&lt;br /&gt;
* Prozessor/Auslastung des Systems&lt;br /&gt;
* Speicher/Cache/Bus&lt;br /&gt;
* Compiler/Optimierer des Compilers (Compiler auf verschiedene Architekturen optimiert?)&lt;br /&gt;
* Geschick des Programmierers&lt;br /&gt;
* Daten (Beispiel Quiclsort: Best case und worst case[Vorsortierter Input] stark unterschiedlich)&lt;br /&gt;
All diese Faktoren sind untereinander abhängig.&lt;br /&gt;
&lt;br /&gt;
Laufzeitvergleiche sind mit Vorsicht zu interpretieren.&lt;br /&gt;
Generell sollten bei Vergleichen möglichst wenige Parameter verändert werden, z.B.&lt;br /&gt;
* gleiches Programm(gleiche Kompilierung), gleiche Daten, andere Prozessoren&lt;br /&gt;
oder&lt;br /&gt;
*gleiche CPU, Daten, andere Programme (Vergleich von Algorithmen)&lt;br /&gt;
&lt;br /&gt;
Beobachtung: Durch Laufzeitmessung ist schwer festzustellen, ob ein Alg prinzipiell besser ist als ein anderer.&lt;br /&gt;
&lt;br /&gt;
== Komplexität ==&lt;br /&gt;
Komplexitätsbetrachtungen ermöglichen den Vergleich der prinzipiellen Eigenschaften von Algorithmen unabhängig von einer Implementation, Umgebung etc.&lt;br /&gt;
      &lt;br /&gt;
Eine einfache Möglichkeit ist das Zählen der Aufrufe einer Schlüsseloperation. Beispiel Sortieren:&lt;br /&gt;
* Anzahl der Vergleiche&lt;br /&gt;
* Anzahl der Vertauschungen&lt;br /&gt;
&lt;br /&gt;
=== Beispiel: Selection Sort ===&lt;br /&gt;
&lt;br /&gt;
  for i in range(len(a)-1):&lt;br /&gt;
    max = i&lt;br /&gt;
    for j in range(i+1, len(a)):&lt;br /&gt;
      if a[j] &amp;lt; a[max]:&lt;br /&gt;
        max = j&lt;br /&gt;
    a[max], a[i] = a[i], a[max]      # swap&lt;br /&gt;
&lt;br /&gt;
*Anzahl der Vergleiche: Ein Vergleich in jedem Durchlauf der inneren Schleife. Es ergibt sich folgende Komplexität:&lt;br /&gt;
*:Ingesamt &amp;lt;math&amp;gt;\sum_{i=0}^{N-2} \sum_{j=i+1}^{N-1}1 = \frac{N}{2} (N-1) \!&amp;lt;/math&amp;gt; Vergleiche.&lt;br /&gt;
&lt;br /&gt;
*Anzahl der Vertauschungen: Eine Vertauschung pro Durchlauf der äußeren Schleife:&lt;br /&gt;
*:Insgesamt &amp;lt;math&amp;gt;N-1 \!&amp;lt;/math&amp;gt; Vertauschungen&lt;br /&gt;
&lt;br /&gt;
Komplexität ist in der Regel eine Funktion der Eingabegröße (Kann auch von der Art der Daten abhängen, nicht nur von der Menge, z.B. vorsortierte Daten bei Quicksort)&lt;br /&gt;
&lt;br /&gt;
=== Fallunterscheidung: Worst und average case ===&lt;br /&gt;
      &lt;br /&gt;
* Komplexität im ungünstigsten Fall&lt;br /&gt;
* Komplexität im durchschnittlichen/typischen Fall&lt;br /&gt;
*: Der typischer Fall ist oft nur schwer oder granicht festlegbar. Es werden dann Approximationen geschaffen, z.B. können alle möglichen Permutationen der Eingabe für Sortieralgorithmen als typischer Fall angenommen werden.&lt;br /&gt;
&lt;br /&gt;
'''Exakte''' Formeln für Komplexität sind schwer zu gewinnen.&lt;br /&gt;
&lt;br /&gt;
=== Beispiele aus den Übungen (Gemessene Laufzeiten für Mergesort/Selectionsort) ===&lt;br /&gt;
&lt;br /&gt;
* Mergesort: &amp;lt;math&amp;gt;\frac{0,977x\log x}{\log 2} + 0,267x-4.39 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
*: andere Lösung: &amp;lt;math&amp;gt;1140*x*log(x) - 1819*x + 6413 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
        &lt;br /&gt;
* Selectionsort: &amp;lt;math&amp;gt;\frac{1}{2}x^2 - \frac{1}{2x} - 10^{-12} \!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
*: andere Lösung: &amp;lt;math&amp;gt;1275x^2 - 116003^x + 11111144 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
In diesen Fällen gibt es also keine offensichtlichen Lösungen (für die Frage welcher Alg besser ist).&lt;br /&gt;
Näherung: Betrachte nur '''sehr große Eingaben''' (Meist sind alle Algorithmen schnell genug für kleine Eingaben). Dieses Vorgehen wird Asymptotische Komplexität bezeichnet (N gegen unendlich).&lt;br /&gt;
&lt;br /&gt;
=== Asymptotische Komplexität am Beispiel Polynom ===&lt;br /&gt;
&lt;br /&gt;
Polynom: &amp;lt;math&amp;gt;ax^2+bx+c=p\!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;math&amp;gt;x \!&amp;lt;/math&amp;gt; sei die Eingabegröße, und wir betrachten die Entwicklung von &amp;lt;math&amp;gt;p \!&amp;lt;/math&amp;gt; in Abhängigkeit von &amp;lt;math&amp;gt;x \!&amp;lt;/math&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
* &amp;lt;math&amp;gt;x=0 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
*: &amp;lt;math&amp;gt;p=c \!&amp;lt;/math&amp;gt;&lt;br /&gt;
* &amp;lt;math&amp;gt;x=1 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
*: &amp;lt;math&amp;gt;p=a+b+c \!&amp;lt;/math&amp;gt;&lt;br /&gt;
* &amp;lt;math&amp;gt;x=1000 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
*: &amp;lt;math&amp;gt;p=1000000a+1000b+c \approx 1000000a\!&amp;lt;/math&amp;gt;&lt;br /&gt;
* &amp;lt;math&amp;gt;x \to \infty \!&amp;lt;/math&amp;gt;&lt;br /&gt;
*: &amp;lt;math&amp;gt;p \approx x^2a\!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Für sehr große Eingaben verlieren also b und c immer mehr an Bedeutung, so dass am Ende nur noch a für die Komplexitätsbetrachtung wichtig ist.&lt;br /&gt;
&lt;br /&gt;
== O-Notation ==&lt;br /&gt;
* Intuitiv: Für große N dominieren die am schnellsten wachsenden Terme.&lt;br /&gt;
* Formal: Eine Funktion &amp;lt;math&amp;gt;f(x) \in O(g(x)) \!&amp;lt;/math&amp;gt;* genau dann wenn es gibt eine Konstante &amp;lt;math&amp;gt;c \!&amp;lt;/math&amp;gt;, so dass &amp;lt;math&amp;gt;f(x) \le cg(x), \forall x &amp;gt; x_0 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Ein einfaches Beispiel ===&lt;br /&gt;
&lt;br /&gt;
[[Image:Sqsqrt.png]]&lt;br /&gt;
&lt;br /&gt;
Rot = &amp;lt;math&amp;gt;x^2 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
Blau = &amp;lt;math&amp;gt;\sqrt{x} \!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;math&amp;gt;\sqrt{x} \in O(x^2)\!&amp;lt;/math&amp;gt; weil &amp;lt;math&amp;gt;\sqrt{x} \le x^2\!&amp;lt;/math&amp;gt; für alle &amp;lt;math&amp;gt;x &amp;lt; x_0 = 1 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Komplexität bei kleinen Eingaben ===&lt;br /&gt;
&lt;br /&gt;
Algorithmus 1: &amp;lt;math&amp;gt;O(N^2) \!&amp;lt;/math&amp;gt;&lt;br /&gt;
Algortihmus 2: &amp;lt;math&amp;gt;=O(N\log{N}) \!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Algorithmus 2 ist schneller (Von geringerer Komplexität), aber bei vielen wiederholten kleinen Eingaben ist Algorithmus 1 schneller.&lt;br /&gt;
&lt;br /&gt;
=== Eigenschaften der O-Notation(Rechenregeln) ===&lt;br /&gt;
&lt;br /&gt;
# Transitiv:&lt;br /&gt;
&amp;lt;math&amp;gt;f(x) \in O(g(x)) \land g(x) \in O(h(x)) \to f(x) \in O(h(x)) \!&amp;lt;/math&amp;gt;           &lt;br /&gt;
&lt;br /&gt;
# Additiv:&lt;br /&gt;
&amp;lt;math&amp;gt;f(x) \in O(h(x)) \land g(x) \in O(h(x)) \to f(x) + g(x) \in O(h(x)) \!&amp;lt;/math&amp;gt;           &lt;br /&gt;
&lt;br /&gt;
# Für Monome gilt:&lt;br /&gt;
        &lt;br /&gt;
&amp;lt;math&amp;gt;x^k \in O(x^k)) \land x^k \in O(x^{k+j}), \forall j \ge 0 \!&amp;lt;/math&amp;gt;&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Effizienz&amp;diff=580</id>
		<title>Effizienz</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Effizienz&amp;diff=580"/>
				<updated>2008-05-08T12:51:47Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: New page: (Vorlesung 7.5.:)  == Laufzeit == Die Laufzeit ist für den Benutzer ein wichtiges Kriterium. Schwierigkeit bei der Bestimmung: Die Laufzeit hängt von vielen Faktoren ab die evtl. nicht k...&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;(Vorlesung 7.5.:)&lt;br /&gt;
&lt;br /&gt;
== Laufzeit ==&lt;br /&gt;
Die Laufzeit ist für den Benutzer ein wichtiges Kriterium.&lt;br /&gt;
Schwierigkeit bei der Bestimmung: Die Laufzeit hängt von vielen Faktoren ab die evtl. nicht kontrollierbar sind:&lt;br /&gt;
* Prozessor/Auslastung des Systems&lt;br /&gt;
* Speicher/Cache/Bus&lt;br /&gt;
* Compiler/Optimierer des Compilers (Compiler auf verschiedene Architekturen optimiert?)&lt;br /&gt;
* Geschick des Programmierers&lt;br /&gt;
* Daten (Beispiel Quiclsort: Best case und worst case[Vorsortierter Input] stark unterschiedlich)&lt;br /&gt;
All diese Faktoren sind untereinander abhängig.&lt;br /&gt;
&lt;br /&gt;
Laufzeitvergleiche sind mit Vorsicht zu interpretieren.&lt;br /&gt;
Generell sollten bei Vergleichen möglichst wenige Parameter verändert werden, z.B.&lt;br /&gt;
* gleiches Programm(gleiche Kompilierung), gleiche Daten, andere Prozessoren&lt;br /&gt;
oder&lt;br /&gt;
*gleiche CPU, Daten, andere Programme (Vergleich von Algorithmen)&lt;br /&gt;
&lt;br /&gt;
Beobachtung: Durch Laufzeitmessung ist schwer festzustellen, ob ein Alg prinzipiell besser ist als ein anderer.&lt;br /&gt;
&lt;br /&gt;
== Komplexität ==&lt;br /&gt;
Komplexitätsbetrachtungen ermöglichen den Vergleich der prinzipiellen Eigenschaften von Algorithmen unabhängig von einer Implementation, Umgebung etc.&lt;br /&gt;
      &lt;br /&gt;
Eine einfache Möglichkeit ist das Zählen der Aufrufe einer Schlüsseloperation. Beispiel Sortieren:&lt;br /&gt;
* Anzahl der Vergleiche&lt;br /&gt;
* Anzahl der Vertauschungen&lt;br /&gt;
&lt;br /&gt;
=== Beispiel: Selection Sort ===&lt;br /&gt;
&lt;br /&gt;
  for i in range(len(a)-1):&lt;br /&gt;
    max = i&lt;br /&gt;
    for j in range(i+1, len(a)):&lt;br /&gt;
      if a[j] &amp;lt; a[max]:&lt;br /&gt;
        max = j&lt;br /&gt;
    a[max], a[i] = a[i], a[max]      # swap&lt;br /&gt;
&lt;br /&gt;
*Anzahl der Vergleiche: Ein Vergleich in jedem Durchlauf der inneren Schleife. Es ergibt sich folgende Komplexität:&lt;br /&gt;
*:Ingesamt &amp;lt;math&amp;gt;\sum_{i=0}^{N-2} \sum_{j=i+1}^{N-1}1 = \frac{N}{2} (N-1) \!&amp;lt;/math&amp;gt; Vergleiche.&lt;br /&gt;
&lt;br /&gt;
*Anzahl der Vertauschungen: Eine Vertauschung pro Durchlauf der äußeren Schleife:&lt;br /&gt;
*:Insgesamt &amp;lt;math&amp;gt;N-1 \!&amp;lt;/math&amp;gt; Vertauschungen&lt;br /&gt;
&lt;br /&gt;
Komplexität ist in der Regel eine Funktion der Eingabegröße (Kann auch von der Art der Daten abhängen, nicht nur von der Menge, z.B. vorsortierte Daten bei Quicksort)&lt;br /&gt;
&lt;br /&gt;
=== Fallunterscheidung: Worst und average case ===&lt;br /&gt;
      &lt;br /&gt;
* Komplexität im ungünstigsten Fall&lt;br /&gt;
* Komplexität im durchschnittlichen/typischen Fall&lt;br /&gt;
*: Der typischer Fall ist oft nur schwer oder granicht festlegbar. Es werden dann Approximationen geschaffen, z.B. können alle möglichen Permutationen der Eingabe für Sortieralgorithmen als typischer Fall angenommen werden.&lt;br /&gt;
&lt;br /&gt;
'''Exakte''' Formeln für Komplexität sind schwer zu gewinnen.&lt;br /&gt;
&lt;br /&gt;
=== Beispiele aus den Übungen (Gemessene Laufzeiten für Mergesort/Selectionsort) ===&lt;br /&gt;
&lt;br /&gt;
* Mergesort: &amp;lt;math&amp;gt;\frac{0,977x\log x}{\log 2} + 0,267x-4.39 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
*: andere Lösung: &amp;lt;math&amp;gt;1140*x*log(x) - 1819*x + 6413 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
        &lt;br /&gt;
* Selectionsort: &amp;lt;math&amp;gt;\frac{1}{2}x^2 - \frac{1}{2x} - 10^{-12} \!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
*: andere Lösung: &amp;lt;math&amp;gt;1275x^2 - 116003^x + 11111144 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
In diesen Fällen gibt es also keine offensichtlichen Lösungen (für die Frage welcher Alg besser ist).&lt;br /&gt;
Näherung: Betrachte nur '''sehr große Eingaben''' (Meist sind alle Algorithmen schnell genug für kleine Eingaben). Dieses Vorgehen wird Asymptotische Komplexität bezeichnet (N gegen unendlich).&lt;br /&gt;
&lt;br /&gt;
=== Asymptotische Komplexität am Beispiel Polynom ===&lt;br /&gt;
&lt;br /&gt;
Polynom: &amp;lt;math&amp;gt;ax^2+bx+c=p\!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;math&amp;gt;x \!&amp;lt;/math&amp;gt; sei die Eingabegröße, und wir betrachten die Entwicklung von &amp;lt;math&amp;gt;p \!&amp;lt;/math&amp;gt; in Abhängigkeit von &amp;lt;math&amp;gt;x \!&amp;lt;/math&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
* &amp;lt;math&amp;gt;x=0 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
*: &amp;lt;math&amp;gt;p=c \!&amp;lt;/math&amp;gt;&lt;br /&gt;
* &amp;lt;math&amp;gt;x=1 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
*: &amp;lt;math&amp;gt;p=a+b+c \!&amp;lt;/math&amp;gt;&lt;br /&gt;
* &amp;lt;math&amp;gt;x=1000 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
*: &amp;lt;math&amp;gt;p=1000000a+1000b+c \approx 1000000a\!&amp;lt;/math&amp;gt;&lt;br /&gt;
* &amp;lt;math&amp;gt;x \to \infty \!&amp;lt;/math&amp;gt;&lt;br /&gt;
*: &amp;lt;math&amp;gt;p \approx x^2a\!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Für sehr große Eingaben verlieren also b und c immer mehr an Bedeutung, so dass am Ende nur noch a für die Komplexitätsbetrachtung wichtig ist.&lt;br /&gt;
&lt;br /&gt;
== O-Notation ==&lt;br /&gt;
* Intuitiv: Für große N dominieren die am schnellsten wachsenden Terme.&lt;br /&gt;
* Formal: Eine Funktion &amp;lt;math&amp;gt;f(x) \in O(g(x)) \!&amp;lt;/math&amp;gt;* genau dann wenn es gibt eine Konstante &amp;lt;math&amp;gt;c \!&amp;lt;/math&amp;gt;, so dass &amp;lt;math&amp;gt;f(x) \le cg(x), \forall x &amp;gt; x_0 \!&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
[[Image:Sqsqrt.png]]&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=File:Sqsqrt.png&amp;diff=579</id>
		<title>File:Sqsqrt.png</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=File:Sqsqrt.png&amp;diff=579"/>
				<updated>2008-05-08T12:51:19Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=577</id>
		<title>Talk:Main Page</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=577"/>
				<updated>2008-05-07T22:12:48Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: Undo revision 576 by 59.151.53.82 (Talk)&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Änderungsvorschläge ==&lt;br /&gt;
&lt;br /&gt;
=== zum Übungsbetrieb ===&lt;br /&gt;
&lt;br /&gt;
Bitte die Email-Adressen der Tutoren eintragen, so wie es schon für Thomas Gerlach der Fall ist.&lt;br /&gt;
:Ich hatte jetzt nur die von Daniel (Do Gruppe) parat, habe sie mal eingetragen [[Special:Contributions/83.189.36.163|83.189.36.163]] 13:41, 13 April 2008 (UTC)&lt;br /&gt;
&lt;br /&gt;
Die Übungen sind ja auch mal wieder extrem einfach und beanspruchen fast grkeine Zeit... Ich sitze jetzt schon so ziemlich den ganzen Tag der zweiten Aufgabe und keine Ende in sicht... als ob wir sonst keine Uni hätten.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Zu Übungsblatt 2:==&lt;br /&gt;
In-place sortieren bei selection- und quick-sort ist mir ja noch einsichtig - aber bei merge-sort? ist der algorithmus nicht so spezifiziert, dass man eine neue liste/ein neues array aufbaut? oder sollen wir einfach noch ne kapsel-funktion schreiben, und die neu-aufgebaute liste am ende auf die ausgangsliste verweisen lassen; das wäre zwar kein in-place sortieren im eigentlichen sinne, aber anders kann ich es mir gerade nicht vorstellen.&lt;br /&gt;
:Also ich denke eher, dass das ein Fehler in der Aufgabenstellung ist. Quick und Merge in-place ist doch schon ziemlich kontroproduktiv...&lt;br /&gt;
&lt;br /&gt;
Vllt. hilft das ja noch jemandem, der mit seinem quick-sort nicht zu Rande kommt: hab die Erfahrung gemacht, dass es keine korrekten Ergebnisse liefert, wenn man die repeat-untils aus der Spezifikation aus der Vorlesung einfach in whiles mit umgekehrter Bedingung macht (also aus repeat...until a[j]&amp;lt;=a[p] etwa while a[j]&amp;gt;a[p]) - python hat zwar keine repeat-untils, aber mit einem while True...und einem den Block abschließenden if a[j]&amp;lt;=a[p]:break kann man das simulieren, und dann kann man einfach die spezifikationen in python eintippen.&lt;br /&gt;
&lt;br /&gt;
== Spam ==&lt;br /&gt;
&lt;br /&gt;
Ich schlage vor einfach mal alle nicht deutsch(sprachig)en IPs zu verbieten, da die Bots wohl aus USA/AU kommen (http://www.who.is/whois-ip/ip-address/208.17.80.5/).&lt;br /&gt;
Ausserdem vorsicht beim reverten, vorhin sind da ein paar Einträge verlorengegangen.&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=575</id>
		<title>Talk:Main Page</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=575"/>
				<updated>2008-05-07T17:42:28Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: /* Spam */ new section&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Änderungsvorschläge ==&lt;br /&gt;
&lt;br /&gt;
=== zum Übungsbetrieb ===&lt;br /&gt;
&lt;br /&gt;
Bitte die Email-Adressen der Tutoren eintragen, so wie es schon für Thomas Gerlach der Fall ist.&lt;br /&gt;
:Ich hatte jetzt nur die von Daniel (Do Gruppe) parat, habe sie mal eingetragen [[Special:Contributions/83.189.36.163|83.189.36.163]] 13:41, 13 April 2008 (UTC)&lt;br /&gt;
&lt;br /&gt;
Die Übungen sind ja auch mal wieder extrem einfach und beanspruchen fast grkeine Zeit... Ich sitze jetzt schon so ziemlich den ganzen Tag der zweiten Aufgabe und keine Ende in sicht... als ob wir sonst keine Uni hätten.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Zu Übungsblatt 2:==&lt;br /&gt;
In-place sortieren bei selection- und quick-sort ist mir ja noch einsichtig - aber bei merge-sort? ist der algorithmus nicht so spezifiziert, dass man eine neue liste/ein neues array aufbaut? oder sollen wir einfach noch ne kapsel-funktion schreiben, und die neu-aufgebaute liste am ende auf die ausgangsliste verweisen lassen; das wäre zwar kein in-place sortieren im eigentlichen sinne, aber anders kann ich es mir gerade nicht vorstellen.&lt;br /&gt;
:Also ich denke eher, dass das ein Fehler in der Aufgabenstellung ist. Quick und Merge in-place ist doch schon ziemlich kontroproduktiv...&lt;br /&gt;
&lt;br /&gt;
Vllt. hilft das ja noch jemandem, der mit seinem quick-sort nicht zu Rande kommt: hab die Erfahrung gemacht, dass es keine korrekten Ergebnisse liefert, wenn man die repeat-untils aus der Spezifikation aus der Vorlesung einfach in whiles mit umgekehrter Bedingung macht (also aus repeat...until a[j]&amp;lt;=a[p] etwa while a[j]&amp;gt;a[p]) - python hat zwar keine repeat-untils, aber mit einem while True...und einem den Block abschließenden if a[j]&amp;lt;=a[p]:break kann man das simulieren, und dann kann man einfach die spezifikationen in python eintippen.&lt;br /&gt;
&lt;br /&gt;
== Spam ==&lt;br /&gt;
&lt;br /&gt;
Ich schlage vor einfach mal alle nicht deutsch(sprachig)en IPs zu verbieten, da die Bots wohl aus USA/AU kommen (http://www.who.is/whois-ip/ip-address/208.17.80.5/).&lt;br /&gt;
Ausserdem vorsicht beim reverten, vorhin sind da ein paar Einträge verlorengegangen.&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=574</id>
		<title>Talk:Main Page</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=574"/>
				<updated>2008-05-07T17:40:41Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: Wieder zu unbespammter Version reverted...&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Änderungsvorschläge ==&lt;br /&gt;
&lt;br /&gt;
=== zum Übungsbetrieb ===&lt;br /&gt;
&lt;br /&gt;
Bitte die Email-Adressen der Tutoren eintragen, so wie es schon für Thomas Gerlach der Fall ist.&lt;br /&gt;
:Ich hatte jetzt nur die von Daniel (Do Gruppe) parat, habe sie mal eingetragen [[Special:Contributions/83.189.36.163|83.189.36.163]] 13:41, 13 April 2008 (UTC)&lt;br /&gt;
&lt;br /&gt;
Die Übungen sind ja auch mal wieder extrem einfach und beanspruchen fast grkeine Zeit... Ich sitze jetzt schon so ziemlich den ganzen Tag der zweiten Aufgabe und keine Ende in sicht... als ob wir sonst keine Uni hätten.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Zu Übungsblatt 2:==&lt;br /&gt;
In-place sortieren bei selection- und quick-sort ist mir ja noch einsichtig - aber bei merge-sort? ist der algorithmus nicht so spezifiziert, dass man eine neue liste/ein neues array aufbaut? oder sollen wir einfach noch ne kapsel-funktion schreiben, und die neu-aufgebaute liste am ende auf die ausgangsliste verweisen lassen; das wäre zwar kein in-place sortieren im eigentlichen sinne, aber anders kann ich es mir gerade nicht vorstellen.&lt;br /&gt;
:Also ich denke eher, dass das ein Fehler in der Aufgabenstellung ist. Quick und Merge in-place ist doch schon ziemlich kontroproduktiv...&lt;br /&gt;
&lt;br /&gt;
Vllt. hilft das ja noch jemandem, der mit seinem quick-sort nicht zu Rande kommt: hab die Erfahrung gemacht, dass es keine korrekten Ergebnisse liefert, wenn man die repeat-untils aus der Spezifikation aus der Vorlesung einfach in whiles mit umgekehrter Bedingung macht (also aus repeat...until a[j]&amp;lt;=a[p] etwa while a[j]&amp;gt;a[p]) - python hat zwar keine repeat-untils, aber mit einem while True...und einem den Block abschließenden if a[j]&amp;lt;=a[p]:break kann man das simulieren, und dann kann man einfach die spezifikationen in python eintippen.&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=529</id>
		<title>Talk:Main Page</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Talk:Main_Page&amp;diff=529"/>
				<updated>2008-05-05T14:03:19Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: Spam gelöscht, reverted&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Änderungsvorschläge ==&lt;br /&gt;
&lt;br /&gt;
=== zum Übungsbetrieb ===&lt;br /&gt;
&lt;br /&gt;
Bitte die Email-Adressen der Tutoren eintragen, so wie es schon für Thomas Gerlach der Fall ist.&lt;br /&gt;
:Ich hatte jetzt nur die von Daniel (Do Gruppe) parat, habe sie mal eingetragen [[Special:Contributions/83.189.36.163|83.189.36.163]] 13:41, 13 April 2008 (UTC)&lt;br /&gt;
&lt;br /&gt;
Die Übungen sind ja auch mal wieder extrem einfach und beanspruchen fast grkeine Zeit... Ich sitze jetzt schon so ziemlich den ganzen Tag der zweiten Aufgabe und keine Ende in sicht... als ob wir sonst keine Uni hätten.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Zu Übungsblatt 2:==&lt;br /&gt;
In-place sortieren bei selection- und quick-sort ist mir ja noch einsichtig - aber bei merge-sort? ist der algorithmus nicht so spezifiziert, dass man eine neue liste/ein neues array aufbaut? oder sollen wir einfach noch ne kapsel-funktion schreiben, und die neu-aufgebaute liste am ende auf die ausgangsliste verweisen lassen; das wäre zwar kein in-place sortieren im eigentlichen sinne, aber anders kann ich es mir gerade nicht vorstellen.&lt;br /&gt;
:Also ich denke eher, dass das ein Fehler in der Aufgabenstellung ist. Quick und Merge in-place ist doch schon ziemlich kontroproduktiv...&lt;br /&gt;
&lt;br /&gt;
Vllt. hilft das ja noch jemandem, der mit seinem quick-sort nicht zu Rande kommt: hab die Erfahrung gemacht, dass es keine korrekten Ergebnisse liefert, wenn man die repeat-untils aus der Spezifikation aus der Vorlesung einfach in whiles mit umgekehrter Bedingung macht (also aus repeat...until a[j]&amp;lt;=a[p] etwa while a[j]&amp;gt;a[p]) - python hat zwar keine repeat-untils, aber mit einem while True...und einem den Block abschließenden if a[j]&amp;lt;=a[p]:break kann man das simulieren, und dann kann man einfach die spezifikationen in python eintippen.&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=Einf%C3%BChrung&amp;diff=305</id>
		<title>Einführung</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=Einf%C3%BChrung&amp;diff=305"/>
				<updated>2008-04-23T17:40:05Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: /* Definition von Datenstrukturen */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Definition von Algorithmen ==&lt;br /&gt;
&lt;br /&gt;
Es gibt viele Definitionen von Algorithmen. Hier sind die Ergebnisse einer Google-Suche auf  [http://www.google.de/search?hl=de&amp;amp;defl=en&amp;amp;q=define:Algorithm&amp;amp;sa=X&amp;amp;oi=glossary_definition&amp;amp;ct=title englisch] und auf&lt;br /&gt;
[http://www.google.de/search?hl=de&amp;amp;defl=de&amp;amp;q=define:Algorithmus&amp;amp;sa=X&amp;amp;oi=glossary_definition&amp;amp;ct=title deutsch]. Die Grundidee ist aber immer gleich:&lt;br /&gt;
&lt;br /&gt;
Ein '''Algorithmus''' ist eine Problemlösung durch endlich viele elementare Schritte. Die Teile der Definition bedürfen näherer Erläuterung:&lt;br /&gt;
&lt;br /&gt;
;Problemlösung: Damit ein Algorithmus ein Problem (genauer: eine Menge von gleichartigen Problemen) lösen kann, muss das Problem zunächst definiert (''spezifiziert'') werden. Die '''Spezifikation''' legt fest, ''was'' der Algorithmus erreichen soll, sagt aber nichts über das ''wie''. Die Spezifikation beschreibt somit relevante Eigenschaften des Systemzustands ''vor'' und ''nach'' der Ausführung des Algorithmus (sogenannte '''Vor-''' und '''Nachbedingungen'''), während der Algorithmus einen bestimmten ''Lösungsweg'' repräsentiert. Mit Hilfe der Spezifikation kann gezeigt werden, dass der Algorithmus tatsächlich eine Lösung des gestellten Problems liefert. Diese Frage untersuchen wir im Kapitel [[Korrektheit]].&lt;br /&gt;
;Endlich viele Schritte: Die Forderung nach endlich vielen Schritten unterstellt, dass jeder einzelne Schritt eine gewisse Zeit benötigt, also nicht unendlich schnell ausgeführt werden kann. Damit ist diese Forderung äquivalent zu der Forderung, dass der Algorithmus in endlicher Zeit zum Ergebnis kommen muss. Der Sinn einer solchen Forderung leuchtet aus praktischer Sicht unmittelbar ein. Interessant ist darüber hinaus die Frage, wie man mit möglichst wenigen Schritten, also möglichst schnell, zur Lösung kommt. Diese Frage untersuchen wir im Kapitel [[Effizienz]].&lt;br /&gt;
;Elementare Schritte: Im weiteren Sinne verstehen wir unter einem elementaren Schritt ein Teilproblem, für das bereits ein Algorithmus bekannt ist. Im engeren Sinne ist die Menge der elementaren Schritte durch die Hilfsmittel vorgegeben, mit denen der Algorithmus ausgeführt werden soll, also z.B. durch die Hardware oder die Programmiersprache. Wir gehen darauf im nächsten Abschnitt näher ein.&lt;br /&gt;
&lt;br /&gt;
=== Zur Frage der elementaren Schritte ===&lt;br /&gt;
&lt;br /&gt;
Welche Schritte als elementar angesehen werden können, hängt sehr stark vom Kontext der Aufgabe und den Hilfsmitteln zu ihrer Lösung ab. Ein interessantes Beispiel ist die Geometrie der alten Griechen, wo geometrische Probleme in der Ebene allein mit Zirkel und Lineal gelöst werden. In diesem Fall sind folgende elementare Operationen erlaubt:&lt;br /&gt;
* das Markieren eines Punktes (beliebig in der Ebene oder als Schnittpunkt zwischen bereits gezeichneten Linien),&lt;br /&gt;
* das Zeichnen einer Geraden durch zwei Punkte,&lt;br /&gt;
* das Zeichnen eines Kreises um einen Punkt,&lt;br /&gt;
* das Abgreifen des Abstands zwischen zwei Punkten mit dem Zirkel.&lt;br /&gt;
Auf der Basis dieser Operationen kann zum Beispiel kein Algorithmus für die Dreiteilung eines beliebigen Winkels definiert werden, während der Algorithmus für die Zweiteilung sehr einfach ist. &lt;br /&gt;
&lt;br /&gt;
Eine völlig andere Menge von elementaren Operationen ergibt sich für arithmetische Berechnungen mit Hilfe des Abacus (Rechenbrett), der seit der Römerzeit in Europa weit verbreitet war. Hier werden Zahlen durch die Positionen von Perlen auf Rillen oder Drähten dargestellt und Berechnungen durch deren Verschiebung. Eine ausführliche Beschreibung der wichtigsten Abacus-Algorithmen findet sich unter [http://webhome.idirect.com/~totton/abacus/ The Bead Unbuffled] von Totton Heffelfinger und Gary Flom.&lt;br /&gt;
&lt;br /&gt;
Die moderne Auffassung von elementaren Operationen wird durch die Berechenbarkeitstheorie (ein Teilgebiet der theoretischen Informatik) bestimmt. Verschiedene Mathematiker (darunter die Pioniere Alan Turing, Alonso Church, Kurt Gödel, Stephen Kleene und Emil Post) haben seit den 1930er Jahren versucht, den intuitiven Begriff der Berechenbarkeit einer Funktion zu formalisieren und sind dabei zu völlig verschiedenen Lösungen gelangt (z.B. Turingmaschine, Lambda-Kalkül, μ-Rekursion und WHILE-Programm). Interessanterweise stellte sich heraus, dass diese Lösungen alle die gleiche Mächtigkeit haben: Obwohl die elementaren Operationen jeweils ganz anders definiert sind, ist die Menge der damit berechenbaren Funktionen immer gleich. Die [http://en.wikipedia.org/wiki/Church_thesis Church-Turing-These] besagt, dass es prinzipiell unmöglich ist, eine mächtigere Definition von elementaren Operationen zu finden, aber dies ist unbewiesen. Am bequemsten für die Praxis sind die  [http://de.wikipedia.org/wiki/WHILE-Programm WHILE-Programme], da sie sich direkt auf die heute gebräuchliche Hardware-Architektur abbilden lassen. Die elementaren Operationen eines WHILE-Programms lauten in erweiterter Backus-Naur Notation:&lt;br /&gt;
 P ::= x[i] = x[j] + c&lt;br /&gt;
     | x[i] = x[j] - c&lt;br /&gt;
     | P; P&lt;br /&gt;
     | WHILE x[i] != 0 DO P DONE&lt;br /&gt;
wobei &amp;lt;tt&amp;gt;c&amp;lt;/tt&amp;gt; ein beliebiges ganzahliges Literal (eine ausgeschriebene ganze Zahl) und &amp;lt;tt&amp;gt;x[i]&amp;lt;/tt&amp;gt; die Speicherzelle &amp;lt;tt&amp;gt;i&amp;lt;/tt&amp;gt; bezeichnet. Alle Speicherzellen können ganze Zahlen aufnehmen und sind anfangs mit Null belegt. Darüber hinaus wird vorausgesetzt, dass mindestens soviele Speicherzellen vorhanden sind, wie der gegebene Algorithmus benötigt, und jede Speicherzelle groß genug ist, um die größte auftretende Zahl aufzunehmen. Beide Annahmen sind in der Praxis nicht immer erfüllt.&lt;br /&gt;
&lt;br /&gt;
Die Zerlegung jedes Problems in Form eines WHILE-Programms (oder eines äquivalenten Formalismus der Berechenbarkeitstheorie) ist für unsere Zwecke aber zu feinkörnig: Sie würde bedeuten, dass alle Algorithmen auf einem sehr einfachen Prozessor in Assembler programmiert werden müssten. Statt dessen definiert man ''höhere Programmiersprachen'', die wichtige Algorithmen wie z.B. die arithmetischen Operationen mit ganzen Zahlen und Gleitkomma-Zahlen bereits als elementare Operationen enthalten. Weitere nicht ganz so wichtige Funktionen wie die Wurzel oder der Logarithmus werden in Programmbibliotheken angeboten, die standardmäßig mitgeliefert werden. In der Praxis betrachtet man eine Operation deshalb als elementar, wenn sie von einer typischen Programmiersprache oder einer typischen Standardbibliothek unterstützt wird. In dieser Vorlesung wählen wir die Operationen und Bibliotheken der Programmiersprache [http://www.python.org Python]. Wenn ein Algorithmus Anforderungen stellt, die nicht selbstverständlich sind, müssen sie als ''Requirements'' explizit angegeben werden. Wir werden darauf im Kapitel [[Generizität]] zurückkommen.&lt;br /&gt;
&lt;br /&gt;
=== Zur Geschichte ===&lt;br /&gt;
&lt;br /&gt;
{| border=&amp;quot;0&amp;quot; cellspacing=&amp;quot;0&amp;quot; cellpadding=&amp;quot;5&amp;quot; &lt;br /&gt;
|-valign=&amp;quot;top&amp;quot; &lt;br /&gt;
| Algorithmen wurden bereits im Altertum verwendet. Besonders die alten Griechen haben Pionierarbeit geleistet, z.B. auf dem Gebiet der Arithmetik (Euklidischer Algorithmus für den größten gemeinsamen Teiler von zwei Zahlen, Sieb des Eratosthenes zur Bestimmung von Primzahlen) und der Geometrie (Teilung einer Strecke oder eines Winkels nur mit Zirkel und Lineal). Der Begriff ''Algorithmus'' ist vom Namen des arabischen Gelehrten Muhammed Al Chwarizmi (ca. 783-850) abgeleitet, der in seinem Werk „Über das Rechnen mit indischen Ziffern“ (um 825) grundlegende Verfahren für das Rechnen im dekadischen Positionssystem beschrieben hat. Im 12. Jahrhundert wurde dieses Buch ins Lateinische übersetzt, und die Einleitung begann mit den Worten „Dixit Algorismi“ (Al Chwarizmi hat gesagt). Ab etwa 1200 wurden die neuen Rechenmethoden als „Algorismus de integris“ bzw. „Algorismus vulgaris“ (Rechnen mit ganzen Zahlen, d.h. Grundrechenarten und Wurzelziehen) sowie „Algorismus de minutiis“ (Bruchrechnung) zum festen Bestandteil der mathematischen Ausbildung im Rahmen der sieben freien Künste. Dabei diente der Begriff Algorithmus unrsprünglich vor allem zur Abgrenzung des schriftlichen Rechnens mit indischen/arabischen Zahlen (wie wir es noch heute in der Schule lernen) vom traditionellen mechanischen Rechnen mit Abacus und römischen Zahlen, das noch bis ca. 1500 in Europa vorherrschend blieb. &lt;br /&gt;
&lt;br /&gt;
Die allgemeinere Bedeutung des Wortes Algorithmus als systematische Rechenvorschrift war jedoch ebenfalls schon früh gebräuchlich. Dies zeigt zum Beispiel der Titel des Buches „Algorismus proportionum“ (Rechenkunst mit Proportionen, ca. 1350) von Nicole Oresme, wo erstmals die Rechenregeln für Potenzen mit rationalen Exponenten beschrieben werden. Durch die steigenden Anforderungen des kaufmännischen Rechnens und der Navigation verbreitete sich die algorithmische Denkweise ab etwa 1500 rasch. Der Buchdruck machte mit Werken wie Adam Ries' „Rechenung auff der linihen und federn“ (d.h. mit Abacus und mit indischen/arabischen Zahlen, zuerst 1522) die grundlegenden Rechenalgorithmen einem breiten Bevölkerungskreis bekannt. Umfangreiche gedruckte Tafelwerke, z.B. der „Canon“ von G.J. Rhaeticus (1551) mit bis zu siebenstelligen Tabellen der trigonometrischen Funktionen, erlaubten es, komplizierte Berechnungen auf einfache Schritte (Addition, Subtraktion sowie Nachschlagen in der Tabelle) zurückzuführen. Unsere heutige Verwendung des Begriffs geht wohl auf Alonso Church's Aufsatz „An Unsolvable Problem of Elementary Number Theory“ (1936) zurück, wo die Berechenbarkeit einer Funktion mit der Existenz eines terminierenden Berechnungsalgorithmus gleichgesetzt wird.&lt;br /&gt;
| [[Image:Al-Khwarizmi.jpg]] &amp;lt;br&amp;gt; Standbild Al Chwarizmis in Teheran&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
== Definition von Datenstrukturen ==&lt;br /&gt;
&lt;br /&gt;
Der Speicher eines Computers enthält eine Folge von Zeichen aus einem gegebenen Alphabet. Bei fast allen heutigen Computern ist dies eine Folge von Bits aus dem Alphabet {0,1}. Eine '''Datenstruktur''' ordnet eine Bitfolge in Gruppen und gibt jeder Gruppe eine Bedeutung. Der Gruppierungsprozess kann dann hierarchisch fortgesetzt werden.&lt;br /&gt;
&lt;br /&gt;
Die selben Bits können somit völlig verschiedene Bedeutungen annehmen, ja nachdem in welcher Datenstruktur sie sich befinden. Man betrachte z.B. die Folge von 32 Bits:&lt;br /&gt;
 11111100011000100110010101101110&lt;br /&gt;
Wenn wir diese Folge als eine einzige Gruppe betrachten und als positive ganze Zahl in Binärdarstellung (unsigned integer) interpretieren, ergibt sich die Dezimalzahl 4234306926. Interpretieren wir dieselbe Gruppe als vorzeichenbehaftete ganze Zahl in [http://de.wikipedia.org/wiki/Zweierkomplement Zweierkomplement]-Darstellung (signed integer), ergibt sich statt dessen die Dezimalzahl -60660370.&amp;lt;br&amp;gt;&lt;br /&gt;
Alternativ können wir die Folge in vier Gruppen zu 8 Bit gruppieren, und die Gruppen als Zeichencodes im Latin-1 Zeichensatz interpretieren. Wir erhalten die Zeichenkette &amp;quot;üben&amp;quot;:&lt;br /&gt;
 11111100 01100010 01100101 01101110 =&amp;gt; üben&lt;br /&gt;
Interpretieren wir dieselben Gruppen hingegen als Farbe im RGBA System, erhalten wir ein halbtransparentes Rosa (Rot: 252, Grün: 98, Blau: 101, Alpha: 110).&amp;lt;br&amp;gt;&lt;br /&gt;
Eine weitere Interpretation ist diejenige als 32-Bit Gleitkommazahl gemäß [http://en.wikipedia.org/wiki/IEEE_floating-point_standard IEEE Standard 754] (float). Dabei wird die Folge in Gruppen zu 1 Bit, 8 Bit und 23 Bit eingeteilt:&lt;br /&gt;
 1 11111000 11000100110010101101110&lt;br /&gt;
Die Gruppen werden als nicht-negative Binärzahlen gelesen, wobei die erste Gruppe das Vorzeichen &amp;lt;tt&amp;gt;s&amp;lt;/tt&amp;gt; der Gleitkommazahl ist (0 bedeutet &amp;quot;+&amp;quot;, 1 bedeutet &amp;quot;-&amp;quot;), die zweite ist ihr Exponent &amp;lt;tt&amp;gt;exp&amp;lt;/tt&amp;gt; und die dritte die Mantisse &amp;lt;tt&amp;gt;m&amp;lt;/tt&amp;gt; (Hier gilt &amp;lt;tt&amp;gt;s = 1&amp;lt;/tt&amp;gt;, &amp;lt;tt&amp;gt;exp = 248&amp;lt;/tt&amp;gt; und &amp;lt;tt&amp;gt;m = 6448494&amp;lt;/tt&amp;gt;). Die Umrechnung in eine Gleitkommazahl erfolgt, gemäß IEEE Standard, nach folgender Formel:&amp;lt;br&amp;gt;&lt;br /&gt;
&amp;lt;tt&amp;gt;z = (1 - 2*s) * 2&amp;lt;sup&amp;gt;exp-127&amp;lt;/sup&amp;gt; * (1 + m * 2&amp;lt;sup&amp;gt;-23&amp;lt;/sup&amp;gt;)&amp;lt;/tt&amp;gt;.&amp;lt;br&amp;gt;&lt;br /&gt;
In Dezimaldarstellung ist dies rund &amp;lt;tt&amp;gt;-4.7020653*10&amp;lt;sup&amp;gt;36&amp;lt;/sup&amp;gt;&amp;lt;/tt&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Im Sinne einer hierarchischen Gruppierung können wir jetzt z.B. eine Datenstruktur &amp;quot;Farbbild&amp;quot; definieren, indem wir viele RGBA-Werte zu einem 2-dimensionalen Array zusammenfassen. Eine Datenstruktur &amp;quot;komplexe Zahl&amp;quot; wird durch ein geordnetes Paar von Gleitkommazahlen gebildet, eine &amp;quot;Meßreihe&amp;quot; als Liste von ganzen Zahlen oder Gleitkommawerten (je nach Art der Messung), usw.&lt;br /&gt;
&lt;br /&gt;
Die Bedeutung der einzelnen Gruppen ist dem Computer normalerweise nicht explizit bekannt. Vielmehr wird sie implizit durch die ''Menge der darauf ausführbaren Operationen'' definiert. Man bezeichnet die Verbindung einer Datenrepräsentation mit einer Menge von erlaubten Operationen als '''(Daten-)Typ''' oder als '''Klasse'''. Programmiersprachen, die ausgereifte Mechanismen zur Definition von Klassen bieten, werden als ''objekt-orientiert'' bezeichnet. Sprachen heißen ''streng typisiert'', wenn der Compiler bzw. Interpreter der Sprache sicherstellt, dass auf jeder Datenstruktur nur die jeweils explizit erlaubten Operationen ausgeführt werden (jeder Versuch, eine illegale Operation auszuführen, wird hier als Fehler signalisiert). Erfolgt diese Prüfung während der Compilierung (also während der Übersetzung des Quellcodes in eine Maschinensprache), spricht man von einer ''statisch typisierten Sprache''. Wird die Prüfung hingegen während der Ausführung des Programms durchgeführt, handelt es sich um eine ''dynamisch typisierte Sprache''. Python ist eine dynamisch-typisierte, objekt-orientierte Sprache. Streng typisiert ist sie allerdings nur für die vordefinierten Klassen. Bei benutzerdefinierten Klassen gibt es (wie bei den meisten anderen Programmiersprachen auch) Möglichkeiten, die erlaubten Operationen zu umgehen. Dies sollte man allerdings nur dann tun, wenn es einen wichtigen Grund gibt. Solange man sich nämlich auf die erlaubten Operationen beschränkt, ist eine große Menge von Fehlerquellen von vornherein ausgeschlossen. &lt;br /&gt;
&lt;br /&gt;
Ein bestimmter Speicherbereich, der den Anforderungen an eine Klasse genügt (wo also die Bits in entsprechender Weise gruppiert und interpretiert werden), wird als '''Objekt''' dieser Klasse oder als '''Instanz''' bezeichnet. Jede Instanz hat eine eindeutige Identität, einen ''Schlüssel''. Innerhalb eines Programms wird dafür gewöhnlich die Speicheradresse des ersten Bytes der Instanz (also der Index der ersten Speicherzelle) verwendet. Dies ist besonders effizient, weil die Speicheradresse für jedes Objekt eindeutig und leicht feststellbar ist. Ist das Objekt hingegen als Datei gespeichert, benötigt man einen expliziten Schlüssel, z.B. den Dateinamen oder die URL. &lt;br /&gt;
&lt;br /&gt;
Das Bitmuster selbst bzw. die daraus folgende Interpretation wird als '''Zustand''' oder '''Wert''' der Instanz bezeichnet. Daraus folgt, dass verschiedene Instanzen einer Klasse dennoch gleiche Werte haben können. Die Menge aller legalen Werte bilden den ''Wertebereich'' der Klasse. Werden Instanzen ausschließlich mit den explizit erlaubten Operationen ihrer Klasse manipuliert, können niemals illegale Werte entstehen. Es liegt auf der Hand, dass illegale Werte schwerwiegende Programmfehler darstellen, die man auf diese Weise vermeidet. [Computerviren tun genau das Gegenteil: Sie verwenden absichtlich verbotene Operationen, um dass Programm in einen illegalen, vom Angreifer gewünschten Zustand zu bringen. Dies ist möglich, weil nicht alle verbotenen Operationen automatisch als Fehler erkannt werden, siehe oben.]&lt;br /&gt;
&lt;br /&gt;
Die meisten Programmiersprachen haben einen oder mehrere spezielle Typen für das Speichern von Objektschlüsseln. Die gebräuchlichsten Namen für diese Typen sind ''Zeiger'' (pointer), ''Referenz'' (reference) und ''Handle''. Wir verwenden das Wort '''Referenz'''. Ein Objekt der Klasse Referenz enthält also den Schlüssel eines anderen Objekts. Man sagt, dass die Referenz ''auf das andere Objekt verweist''. Diese Art der Indirektion ist uns heutzutage durch das Internet bestens vertraut: Jede WWW-Seite ist ein Objekt, und seine URL ist der dazugehörige Schlüssel. Hyperlinks und Lesezeichen (bookmarks) hingegen sind Referenzen, die mittels der URL auf andere Seiten verweisen.&lt;br /&gt;
&lt;br /&gt;
Aus der Unterscheidung von Werten und Referenzen ergibt sich die wichtige Unterscheidung von ''Wertsemantik'' und ''Referenzsemantik''. Wird nämlich ein Objekt an eine Variable zugewiesen&lt;br /&gt;
 x = anObject&lt;br /&gt;
so hängt die korrkte Verwendung der Variablen &amp;lt;tt&amp;gt;x&amp;lt;/tt&amp;gt; davon ab, ob sie das Objekt in Form eines Wertes oder einer Referenz speichert. Im ersten Fall wird das Objekt selbst kopiert, und es entsteht ein neues Objekt mit neuer Identität, aber gleichem Zustand. Im andern Fall wird nur der Schlüssel kopiert, und die Referenz verweist nach wie vor auf das ursprüngliche Objekt. Ist &amp;lt;tt&amp;gt;x&amp;lt;/tt&amp;gt; ein Wert, so verändert eine Manipulation von &amp;lt;tt&amp;gt;x&amp;lt;/tt&amp;gt; nur das neue Objekt (das ursprüngliche bleibt erhalten). Ist &amp;lt;tt&amp;gt;x&amp;lt;/tt&amp;gt; hingegen eine Referenz, wird immer das ürsprüngliche Objekt manipuliert (denn es gibt ja keine Kopie). Ob eine Variable einen Wert oder eine Referenz enthält, wird in jeder Programmiersprache anderes festgelegt. In Python gilt&lt;br /&gt;
* Zahlen (Typen &amp;lt;tt&amp;gt;bool&amp;lt;/tt&amp;gt;, &amp;lt;tt&amp;gt;int&amp;lt;/tt&amp;gt;, und &amp;lt;tt&amp;gt;float&amp;lt;/tt&amp;gt;) werden immer als Werte gespeichert und kopiert.&lt;br /&gt;
* Alle anderen Typen werden als Referenzen gespeichert und kopiert.&lt;br /&gt;
* Für alle Typen kann Wertsemantik mit Hilfe des Python-Moduls [http://docs.python.org/lib/module-copy.html copy] erzwungen werden.&lt;br /&gt;
Das Verständnis von Werten und Referenzen wird in der 1. Übung vertieft.&lt;br /&gt;
&lt;br /&gt;
Der Entwurf von Datentypen wird uns im Laufe der Vorlesung immer wieder beschäftigen.&lt;br /&gt;
&lt;br /&gt;
[[Image:Dt dreieck.png]]&lt;br /&gt;
&lt;br /&gt;
== Fundamentale Algorithmen ==&lt;br /&gt;
&lt;br /&gt;
Einige Algorithmen werden praktisch bei jeder Klasse benötigt, unabhängig vom eigentlichem Verwendungszweck der Klasse. Es ist wichtig, diese fundamentalen Algorithmen zu kennen. Außerdem eignen sie sich gut zur Einführung der Grundprinzipien der Algorithmen-Spezifikation mittels Vor- und Nachbedingungen. Diese Bedingungen beschreiben Eigenschaften, die die Variablen des Systems ''vor'' bzw. ''nach'' der Ausführung des Algorithmus haben sollen. Damit man außerdem die Veränderungen durch den Algorithmus beschreiben kann, führt man zu jeder Variablen (z.B. &amp;lt;tt&amp;gt;x&amp;lt;/tt&amp;gt;) eine Hilfsvariable (z.B. &amp;lt;tt&amp;gt;x&amp;lt;sub&amp;gt;o&amp;lt;/sub&amp;gt;&amp;lt;/tt&amp;gt;, sprich &amp;quot;x-old&amp;quot;) ein. In den Hilfsvariablen wird der Zustand ''vor'' der Ausführung des Algorithmus gespeichert, so dass man diesen noch abfragen kann, wenn Variablen durch den Algorithmus verändert werden. Wenn der Algorithmus beispielsweise die Variable &amp;lt;tt&amp;gt;x&amp;lt;/tt&amp;gt; inkrementiert (um eins erhöht), gilt die Nachbedingung &amp;lt;tt&amp;gt;x == x&amp;lt;sub&amp;gt;o&amp;lt;/sub&amp;gt; + 1&amp;lt;/tt&amp;gt; (darin ist &amp;lt;tt&amp;gt;x&amp;lt;/tt&amp;gt; der neue, und &amp;lt;tt&amp;gt;x&amp;lt;sub&amp;gt;o&amp;lt;/sub&amp;gt;&amp;lt;/tt&amp;gt; der alte Wert der Variablen). Falls &amp;lt;tt&amp;gt;x&amp;lt;/tt&amp;gt; hingegen nicht verändert wird, gilt &amp;lt;tt&amp;gt;x == x&amp;lt;sub&amp;gt;o&amp;lt;/sub&amp;gt;&amp;lt;/tt&amp;gt;. (Man beachte, dass dies in der Literatur nicht einheitlich gehandhabt wird -- einige Autoren verwenden z.B. &amp;lt;tt&amp;gt;x&amp;lt;/tt&amp;gt; für den Zustand vor Ausführung des Algorithmus, und &amp;lt;tt&amp;gt;x'&amp;lt;/tt&amp;gt; für denjenigen danach. Diese Syntax ist jedoch mit den meisten Programmiersprachen inkompatibel.)&lt;br /&gt;
&lt;br /&gt;
Die wichtigste Gruppe von fundamentalen Funktionen sind die '''Konstruktoren''', die einen vorher unbenutzten Speicherbereich in eine Datenstruktur mit einem wohldefinierten Anfangswert transformieren. In Python haben die Konstruktoren im allgemeinen den gleichen Namen wie die dazugehörige Klasse, also z.B.&lt;br /&gt;
 i = int()   # erzeuge eine ganze Zahl mit Anfangswert 0&lt;br /&gt;
 f = float() # erzeuge eine Gleitkommazahl mit Anfangswert 0&lt;br /&gt;
 a = list()  # erzeuge ein leeres Array&lt;br /&gt;
usw. (Man beachte, dass das Python-Array den Klassennamen &amp;lt;tt&amp;gt;list&amp;lt;/tt&amp;gt; hat. Dies hat nichts mit verketteten Listen zu tun.) Konstruktoren ohne Argumente bezeichnet man als ''Standard-Konstruktoren'' (default constructors). Ja nach Typ gibt es meist noch weitere Konstruktoren, die Objekte mit anderen Anfangswerten erzeugen, z.B.&lt;br /&gt;
 i = int(2)     # erzeuge eine ganze Zahl mit Anfangswert 2&lt;br /&gt;
 i = 2          # ebenso (abgekürzte Schreibweise)&lt;br /&gt;
 f = float(1.5) # erzeuge eine Gleitkommazahl mit Anfangswert 1.5&lt;br /&gt;
 f = 1.5        # ebenso (abgekürzte Schreibweise)&lt;br /&gt;
 a = [i, f]     # erzeuge ein Array mit Kopien der Werte von i und f&lt;br /&gt;
(Das Array &amp;lt;tt&amp;gt;a&amp;lt;/tt&amp;gt; enthält Kopien der Werte, weil Zahlen immer mit Wertsemantik zugewiesen werden.) Die allgemeine Spezifikation eines Standard-Konstruktors lautet&lt;br /&gt;
&lt;br /&gt;
&amp;lt;math&amp;gt;\begin{array}{ll}&lt;br /&gt;
\mathrm{Precondition: } &amp;amp; T \in \mathrm{Types}\\&lt;br /&gt;
\mathrm{Constructor: } &amp;amp; t = T() \\&lt;br /&gt;
\mathrm{Postcondition: } &amp;amp; t \in T&lt;br /&gt;
\end{array}&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Der Ausdruck &amp;lt;math&amp;gt;t \in T&amp;lt;/math&amp;gt; besagt, dass t nach Ausführung des Konstruktors eine legale Instanz des Typs T (oder eine Referenz auf einen solche Instanz) sein muss. In Pythonsyntax kann dies folgendermassen geschrieben werden&lt;br /&gt;
 import inspect           # wir brauchen das inspect-Modul&lt;br /&gt;
 &lt;br /&gt;
 if inspect.isclass(T):   # prüfe, dass T ein Type ist&lt;br /&gt;
      t = T()&lt;br /&gt;
 assert isinstance(t, T)&lt;br /&gt;
Natürlich funktioniert der Code nur, wenn die Klasse &amp;lt;tt&amp;gt;T&amp;lt;/tt&amp;gt; tatsächlich existiert und dafür ein Standardkonstruktor definiert wurde. Das Gegenstück zu Konstruktoren sind die '''Destruktoren''', die den Speicher der Datenstruktur wieder frei geben. Da Python automatisches Speichermanagment unterstützt, werden die Destruktoren automatisch aufgerufen. Wir können sie deshalb hier übergehen.&lt;br /&gt;
&lt;br /&gt;
Sehr wichtig sind auch die '''Vergleichsoperatoren'''. Wir müssen dabei unterscheiden, ob auf Gleichheit der Referenzen (''identity'') oder auf Gleichkeit der Werte (''equality'') geprüft werden soll. In Python werden dazu die Operatoren &amp;lt;tt&amp;gt;is&amp;lt;/tt&amp;gt; bzw. &amp;lt;tt&amp;gt;==&amp;lt;/tt&amp;gt; verwendet. Die Negation erhält man durch &amp;lt;tt&amp;gt;is not&amp;lt;/tt&amp;gt; bzw. &lt;br /&gt;
&amp;lt;tt&amp;gt;!=&amp;lt;/tt&amp;gt;&lt;br /&gt;
 a = [1, 2]&lt;br /&gt;
 b = [1, 2]&lt;br /&gt;
 &lt;br /&gt;
 a == b      # True  weil gleiche Werte&lt;br /&gt;
 a != b      # False weil Negation&lt;br /&gt;
 a is b      # False weil unterschiedliche Identität&lt;br /&gt;
 a is not b  # True  weil Negation&lt;br /&gt;
&lt;br /&gt;
(Beachte: beim Vergleich von Zahlen des gleichen Typs liefern &amp;lt;tt&amp;gt;is&amp;lt;/tt&amp;gt; und &amp;lt;tt&amp;gt;==&amp;lt;/tt&amp;gt; immer dasselbe Ergebnis.) Natürlich impliziert die Gleichheit der Schlüssel (Identität der Objekte) die Gleichheit der Werte.&lt;br /&gt;
&lt;br /&gt;
Ebenso wichtig sind die '''Zuweisungen'''. Hier zeigt sich besonders der Unterschied zwischen Wert- und Referenzsemantik. Im Falle von Wertsemantik gilt&lt;br /&gt;
&lt;br /&gt;
&amp;lt;math&amp;gt;\begin{array}{ll}&lt;br /&gt;
\mathrm{Preconditions: } &amp;amp; s,t \in T \\&lt;br /&gt;
                         &amp;amp; s \mathrm{\ is\ not\ } t \\&lt;br /&gt;
\mathrm{Assign\ by\ value: } &amp;amp; s = t \\&lt;br /&gt;
\mathrm{Postconditions: } &amp;amp; t \mathrm{\ is\ } t_o \\&lt;br /&gt;
                          &amp;amp; s \mathrm{\ is\ not\ } t \\&lt;br /&gt;
                          &amp;amp; s == t &lt;br /&gt;
\end{array}&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Das heisst, t darf sich nicht verändern, und s hat nach der Zuweisung den gleichen Wert wie t. Bei Referenzsemantik gilt sogar&lt;br /&gt;
&lt;br /&gt;
&amp;lt;math&amp;gt;\begin{array}{ll}&lt;br /&gt;
\mathrm{Precondition: } &amp;amp; t \in T \\&lt;br /&gt;
\mathrm{Assign\ by\ reference: } &amp;amp; s = t \\&lt;br /&gt;
\mathrm{Postconditions: } &amp;amp; t \mathrm{\ is\ } t_o \\&lt;br /&gt;
                          &amp;amp; s \mathrm{\ is\ } t&lt;br /&gt;
\end{array}&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Dies entspricht dem Pythoncode&lt;br /&gt;
 x = y&lt;br /&gt;
 assert x is y&lt;br /&gt;
Die Wertsemantik muss man in Python explizit erzwingen&lt;br /&gt;
 import copy  # wir brauchen das copy-Modul&lt;br /&gt;
 &lt;br /&gt;
 x = copy.deepcopy(y)&lt;br /&gt;
 assert x == y&lt;br /&gt;
 assert x is not y&lt;br /&gt;
&lt;br /&gt;
Mit der Zuweisung eng verwandt ist die Funktion &amp;lt;tt&amp;gt;swap&amp;lt;/tt&amp;gt;, die den Inhalt von zwei Variablen vertauscht:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;math&amp;gt;\begin{array}{ll}&lt;br /&gt;
\mathrm{Precondition: } &amp;amp; t \in T, s \in S \\&lt;br /&gt;
\mathrm{Algorithm\ swap: } &amp;amp; \mathrm{swap}(s, t) \\&lt;br /&gt;
\mathrm{Postconditions: } &amp;amp; t \mathrm{\ is\ } s_o \\&lt;br /&gt;
                          &amp;amp; s \mathrm{\ is\ } t_o&lt;br /&gt;
\end{array}&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Diese Funktion wird sich beim Sortieren als sehr nützlich erweisen, weil dort das Vertauschen von zwei Datenelementen eine Grundoperation ist. In Python kann man dies so implementieren:&lt;br /&gt;
 t, s = s, t  # swap&lt;br /&gt;
Dabei macht man sich zunutze, dass Python mehrere Variablen in einem einzigen Statement zuweisen kann.&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	<entry>
		<id>https://alda.iwr.uni-heidelberg.de/index.php?title=File:Dt_dreieck.png&amp;diff=304</id>
		<title>File:Dt dreieck.png</title>
		<link rel="alternate" type="text/html" href="https://alda.iwr.uni-heidelberg.de/index.php?title=File:Dt_dreieck.png&amp;diff=304"/>
				<updated>2008-04-23T17:39:10Z</updated>
		
		<summary type="html">&lt;p&gt;Alter: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Alter</name></author>	</entry>

	</feed>