Zitat von
Salazriel:
Delphi-Quellcode:
For i:=1 to 9 do
If (i in FeldMenge[x,y]) and not (((i+1) mod 9) in FeldMenge[x,y]) and not (((i+2) mod 9) in FeldMenge[x,y]){.....
....} and not (((i+8) mod 9) in FeldMenge[x,y]) then GibZahlaus ;
Das muss doch eleganter gehen!
Ja, das geht deutlich eleganter, vor allem schneller, ist aber etwas tricky und nicht beliebig auf ähnliche Probleme übertragbar.
Delphi-Quellcode:
function SingleValueInSet(v:zahlen):integer;
begin
result:=0;
if (Word(v)>0) and (Word(v) and (Word(v)-1) = 0) then // dann ist nur ein Wert im Set
while not odd(word(v)) do begin
inc(result);
Word(v):=Word(v) shr 1;
end;
end;
Der erste Teil (Prüfung ob nur ein Bit im Set gesetzt ist) stammt nicht von mir (von negah).
Und die folgende Assembler Version dürfte erheblich schneller sein.
Delphi-Quellcode:
function ASingleValueInSet(v:zahlen):integer;
asm
movzx edx,ax
// v auf Cardinal erweitert in EDX
bsf eax,edx
// Index des untersten gesetzten Bits in EAX
bsr edx,edx
// Index des obersten gesetzten Bits in EDX
xor edx,eax
// Wenn mehrere Bits gesetzt sind (oder keins, oder Bit 0), ist ZF=1
jz @
end // Nur 1 Bit gesetzt, (EAX enthält den Wert) oder keins oder Bit 0 (und EAX ist 0)
xor eax,eax
@
end:
end;