Minimum/Maximum einer Reihe von Werten bestimmen

Für allgemeine Fragen zur Programmierung mit PureBasic.
Benutzeravatar
jacdelad
Beiträge: 404
Registriert: 03.02.2021 13:39
Wohnort: Riesa
Kontaktdaten:

Minimum/Maximum einer Reihe von Werten bestimmen

Beitrag von jacdelad »

Ich hab ein paar Koordinaten (4 an der Zahl), von denen jeweils die Minimum-/Maximum-Werte bestimmt werden sollen:

Code: Alles auswählen

Structure Rechteck
  left.l
  right.l
  top.l
  bottom.l
EndStructure
Define a.POINT,b.POINT,c.POINT,d.POINT,max.Rechteck

;Schleife
;Koordinatenermittlung
  If a\x<max\left:max\left=a\x:ElseIf a\x>max\right:max\right=a\x:EndIf
  If b\x<max\left:max\left=b\x:ElseIf b\x>max\right:max\right=b\x:EndIf
  If c\x<max\left:max\left=c\x:ElseIf c\x>max\right:max\right=c\x:EndIf
  If d\x<max\left:max\left=d\x:ElseIf d\x>max\right:max\right=d\x:EndIf
  If a\y<max\top:max\top=a\y:ElseIf a\y>max\bottom:max\bottom=a\y:EndIf
  If b\y<max\top:max\top=b\y:ElseIf b\y>max\bottom:max\bottom=b\y:EndIf
  If c\y<max\top:max\top=c\y:ElseIf c\y>max\bottom:max\bottom=c\y:EndIf
  If d\y<max\top:max\top=d\y:ElseIf d\y>max\bottom:max\bottom=d\y:EndIf
;Schleife Ende
;Weiterverarbeitung
Gibt es da vielleicht eine effizientere Möglichkeit?
Guten Morgen, das ist ein schöner Tnetennba!

PureBasic 6.21/Windows 11 x64/Ryzen 7900X/32GB RAM/3 TB SSD
Synology DS1821+/DX517, 130.9TB+50.8TB+2TB SSD
Benutzeravatar
STARGÅTE
Kommando SG1
Beiträge: 7035
Registriert: 01.11.2005 13:34
Wohnort: Glienicke
Kontaktdaten:

Re: Minimum/Maximum einer Reihe von Werten bestimmen

Beitrag von STARGÅTE »

Schreib dir noch einfach eine Min und Max Funktion mit 4 Parametern, dann kannst du ja dein "max" wie folgt ausrechnen:

Code: Alles auswählen

max\left = Min(a\x, b\x, c\x, d\x)
PB 6.01 ― Win 10, 21H2 ― Ryzen 9 3900X, 32 GB ― NVIDIA GeForce RTX 3080 ― Vivaldi 6.0 ― www.unionbytes.de
Aktuelles Projekt: Lizard - Skriptsprache für symbolische Berechnungen und mehr
Benutzeravatar
jacdelad
Beiträge: 404
Registriert: 03.02.2021 13:39
Wohnort: Riesa
Kontaktdaten:

Re: Minimum/Maximum einer Reihe von Werten bestimmen

Beitrag von jacdelad »

Ja, das habe ich auch schon überlegt, aber schneller ist das nicht.
Guten Morgen, das ist ein schöner Tnetennba!

PureBasic 6.21/Windows 11 x64/Ryzen 7900X/32GB RAM/3 TB SSD
Synology DS1821+/DX517, 130.9TB+50.8TB+2TB SSD
GPI
Beiträge: 1511
Registriert: 29.08.2004 13:18
Kontaktdaten:

Re: Minimum/Maximum einer Reihe von Werten bestimmen

Beitrag von GPI »

ein Macro könnte das einfacher zum schreiben machen.

Code: Alles auswählen

Macro SetMax(_a_,_max_)
  If _a_\x < _max_\left : _max_\left = _a_\x : ElseIf _a_\x > _max_\right : _max_\right = _a_\x : EndIf
  If _a_\y < _max_\top : _max_\top = _a_\y : ElseIf _a_\y > _max_\bottom : _max_\bottom = _a_\y : EndIf
Endmacro

; Beim ersten mal nicht das Macro setzen, sondern direkt die werte! Der Punkt ist ja aktuell der kleinste *UND* größte Punkt!
max\left = a\x : max\right = a\x
max\top = a\y : max\bottom = a\y
; die restlichen einfach überprüfen lassen.
SetMax(b,max)
SetMax(c,max)
SetMax(d,max)
schneller ist es nicht, aber auch nicht langsamer, dafür aber besser lesbar und damit wartbar.

Wenns wirklich nur 4 Werte sind, dann kannst du folgendes probieren:

Code: Alles auswählen

IF a/x < b/x
  IF c/x < d /x
    ;a und c sind kleinste
    IF a/x < c/x
      max\left = a/x
    else
      max\left= c/x
    endif
    ; und gleichzeitig B und D die größten
    IF b/x > d/x
      max\right = b/x
    else
      max\right = d/x
    endif
  else
    ;a und d sind die kleinsten
    IF a/x < d/x
      max\left = a/x
    else
      max\left = d/x
    endif
    ; und gleichzeitig B und c die größten
    IF b/x > c/x
      max\right = b/x
    else
      max\right = c/x
    endif
  endif
else
   IF c/x < d /x
    ;b und c sind kleinste
    IF b/x < c/x
      max/left = b/x
    else
      max/left = c/x
    endif
    ; und gleichzeitig a und D die größten
    IF a/x > d/x
      max\right = a/x
    else
      max\right = d/x
    endif
  else
    ;b und d sind die kleinsten
    IF b/x < d/x
      max\left = b/x
    else
      max\left = d/x
    endif
    ; und gleichzeitig a und c die größten
    IF a/x > c/x
      max\right = a/x
    else
      max\right = c/x
    endif
  endif
endif
DAS ist aber dann schlecht wartbar! Reduziert aber die IF-Abfragen auf ein minium und auch das setzen der max variable. Würd ich aber nur machen, wenn du wirklich viele 4er-Punkte so abarbeiten musst.
Falls du ein Absolutes Max über viele 4er-Punkte willst, musst du an den Stellen, wo MAX\Left und MAX\Right gesetzt werden, noch überprüfen, ob das alte MAX\LEFT / Max\Right überhaupt kleiner ist als der ermittelte Punkt. Für TOP/BOT gehts analog.
Könntest auch ein Macro machen, indem du dann die Structure-Felder angibst.

Code: Alles auswählen

macro Check( _xy_, _lefttop_, rightbottom_)
IF a/_xy_ < b/_xy_
  IF c/_xy_ < d /_xy_
    ;a und c sind kleinste
    IF a/_xy_ < c/_xy_
      max\_lefttop_ = a/_xy_
  [...] usw. [...]
endmacro

check(x, left, right)
check(y, top, bottom)

Und setz kommentare - das hilft bei späteren Warten ungemein :)
CodeArchiv Rebirth: Deutsches Forum Github Hilfe ist immer gern gesehen!
GPI
Beiträge: 1511
Registriert: 29.08.2004 13:18
Kontaktdaten:

Re: Minimum/Maximum einer Reihe von Werten bestimmen

Beitrag von GPI »

oder ums allgemeiner zu halten:

Code: Alles auswählen

EnableExplicit
Macro GetMinMax(_a_,_b_,_c_,_d_,_min_,_max_)
  If _a_ < _b_
    If _c_ < _d_ 
      ;a und c sind die kleinsten
      If _a_ < _c_
        _min_ = _a_
      Else
        _min_= _c_
      EndIf
      ; und gleichzeitig B und D die größten
      If _b_ > _d_
        _max_ = _b_
      Else
        _max_ = _d_
      EndIf
    Else
      ;a und d sind die kleinsten
      If _a_ < _d_
        _min_ = _a_
      Else
        _min_ = _d_
      EndIf
      ; und gleichzeitig B und c die größten
      If _b_ > _c_
        _max_ = _b_
      Else
        _max_ = _c_
      EndIf
    EndIf
  Else
    If _c_ < _d_ 
      ;b und c sind die kleinsten
      If _b_ < _c_
        _min_ = _b_
      Else
        _min_ = _c_
      EndIf
      ; und gleichzeitig a und D die größten
      If _a_ > _d_
        _max_ = _a_
      Else
        _max_ = _d_
      EndIf
    Else
      ;b und d sind die kleinsten
      If _b_ < _d_
        _min_ = _b_
      Else
        _min_ = _d_
      EndIf
      ; und gleichzeitig a und c die größten
      If _a_ > _c_
        _max_ = _a_
      Else
        _max_ = _c_
      EndIf
    EndIf
  EndIf
EndMacro

Define.point a,b,c,d
Define.rect max

a\x = Random(1000)-500
a\y = Random(1000)-500
b\x = Random(1000)-500
b\y = Random(1000)-500
c\x = Random(1000)-500
c\y = Random(1000)-500
d\x = Random(1000)-500
d\y = Random(1000)-500

Debug ""+a\x+" "+a\y
Debug ""+b\x+" "+b\y
Debug ""+c\x+" "+c\y
Debug ""+d\x+" "+d\y

Debug" ---- "
GetMinMax(a\x, b\x, c\x, d\x, max\left, max\right)
GetMinMax(a\y, b\y, c\y, d\y, max\top, max\bottom)
Debug ""+max\left+" - "+max\right+" x "+max\top+" - "+max\bottom
bitte beachten, das ist ein Macro.
ein "GetMaxMin( a+b, c+d, e+f, min, max)" würde funktionieren, aber überall wo ein "_a_" steht würde dann "a+b" stehen und es würden x unnötige Additionen erfolgen. Ansonsten ist das Maco jetzt universell anwendbar. Würde bspw. auch mit Strings funktionieren!
CodeArchiv Rebirth: Deutsches Forum Github Hilfe ist immer gern gesehen!
Benutzeravatar
jacdelad
Beiträge: 404
Registriert: 03.02.2021 13:39
Wohnort: Riesa
Kontaktdaten:

Re: Minimum/Maximum einer Reihe von Werten bestimmen

Beitrag von jacdelad »

Danke für die Ansätze, aber das macht's nicht wirklich schneller oder effizienter und nur bedingt lesbarer. Aber das ist auch nicht schlimm, dann bleibt es wie es ist.
Guten Morgen, das ist ein schöner Tnetennba!

PureBasic 6.21/Windows 11 x64/Ryzen 7900X/32GB RAM/3 TB SSD
Synology DS1821+/DX517, 130.9TB+50.8TB+2TB SSD
Antworten