Entwickler-Ecke

Algorithmen, Optimierung und Assembler - Wasseruhr


steppenwolf - Di 14.06.05 15:14
Titel: Wasseruhr
Hallo allerseits,

ich dreh am Rad: Ich soll eine 'Wasseruhr' programmieren, wobei die Anzahl der Ziffern variabel sein soll. Außerdem soll mit der linken Zahl begonnen werden zu zählen.

Ich komme mit einer Doppelschleife und einem eindimensionalen Array einfach nicht hin, da ja nicht alle Kombinationen erfaßt werde. Für Hinweise vielen Dank im Voraus.

Auf bald ...
steppenwolf.


GTA-Place - Di 14.06.05 15:18

Wenn du mir erklärst, was nochmal eine 'Wasseruhr' ist, kann ich vielleicht helfen :-)


F34r0fTh3D4rk - Di 14.06.05 15:46

ich glaube er meint das http://de.wikipedia.org/wiki/Wasseruhr


arj - Di 14.06.05 16:28

Wie wäre es mit:


Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
var zahl : Integer;
    s : String;
[...]

function Reverse(str:String):String;
var i : Integer;
begin
  for i := Length(str) downto 1 do
    Result := Result + str;
end;

s := Reverse(Format('%.'+IntToStr(anzahl_ziffern)+'d',[zahl]));
// s kannst du als ausgabe verwenden


Und zum hochzählen:


Delphi-Quelltext
1:
inc(i);                    


Hoffe ich hatte dich richtig verstanden

Moderiert von user profile iconChristian S.: Code- durch Delphi-Tags ersetzt.


F34r0fTh3D4rk - Di 14.06.05 16:42

@steppenwolf: wie wäre es mit ein wenig code, damit auch wir es verstehen ?


steppenwolf - Di 14.06.05 17:25

Hallo allerseits,

sorry für meine etwas abstrakte Darstellung und Danke für die bisherigen Infos.

Also, ich habe ein eindimensionales Array definiert und möchte alle Varianten durchzählen.

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
// Initialisieren
for i := 1 to Stellenzahl do Wasseruhr [i] := 0;

// Durchzählen
for i := 1 to Stellenzahl do
begin
  for j := 0 to 9 do
  begin
    Wasseruhr [i] := j;
  end;
end;


Problem ist, daß nach dem Durchlauf der ersten Stelle diese ja bei 9 'stehenbleibt'. Bei einer dreistelligen Anzahl würden nur dreißig Durchläufe stattfinden anstatt der 999 (bzw. 1000).

Auf bald ...
steppenwolf.

Moderiert von user profile iconChristian S.: Delphi-Tags hinzugefügt.


delfiphan - Di 14.06.05 17:28

Wenn du jede Stelle separat behandelst kriegst du das nicht mit einer Doppelschleife hin.
5 Stellen => 10*10*10*10*10 Werte => Du brauchst 5 verschachtelte Schleifen à 10 Durchläufen.
Machs mit Rekursionen, oder Iterativ wie user profile iconarj. Int64 wäre zu empfehlen.


alzaimar - So 19.06.05 13:05

Oder, schreibe Dir eine Prozedur, die die Addition mit Überlauf beherrscht. Wenn ich das richtig verstanden habe:

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
22:
23:
24:
25:
26:
27:
28:
29:
30:
Procedure ArrayInc (aNumber : Array Of Integer); // Zählerstellen in aNumber, einer-Stelle in aNumber[0];
Var
  i : Integer;

Begin
  i := 0;                        // Bei der 1. Stelle beginnen
  While i< High (aNumber) do    
    if aNumber[i]=9 Then Begin   // i.te Stelle ist 'voll' 
      aNumber[i] := 0;           // wieder 'leeren' und bei der
      inc (i);                   // nächsten Stelle weitermachen
      End
    Else begin
     inc (aNumber[i]);           // ansonsten normale Addition
     Exit;
     End;
  
  Raise Exception.Create('Überlauf!')
End;

Procedure Test;
Var
  aZaehler : Array [0..5Of Integer;

Begin
  FillChar (aZaehler, SizeOf (aZaehler), 0);
  While True Do Begin
    ArrayInc (aZaehler);
    ZeigeZaehlerstand (aZaehler);
    End;
End;

Die Testroutine ruft den Addiere einfach auf, bis ein Überlauf eintritt ('999999' + 1)


steppenwolf - Do 07.07.05 16:51

Hallo allerseits,

vielen Dank für Eure Tips.

Ich habe eine Alternative gefunden:


Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
  Anzahl_Buffer := (Potenz (10, Anzahl));   // Zehn Hoch Anzahl  bspw. 10^3
  for i := 1 to Anzahl_Buffer - 1 do

  begin
    Wasseruhr_String := IntToStr (i);
    Stringlaenge_Buffer := Length(Wasseruhr_String);

    // Befüllung des Arrays
    k := Anzahl;
    Position := Stringlaenge_Buffer;

    for j := Stringlaenge_Buffer downto 1 do
    begin
      Wasseruhr [k] := StrToInt (Copy (Wasseruhr_String, Position, 1));
      Dec (Position);
      Dec (k);
    end;

  end;

Auf bald ...
steppenwolf.

Moderiert von user profile iconGausi: Delphi-Tags hinzugefügt.


zemy - Fr 08.07.05 09:58

Gut, nciht gerade elegant aber funktioniert .... Fasse deine Beiträge ,mit Delphiquellcode allerdings besser in Delphi-Tags, ist besser Lesbar..