Entwickler-Ecke

Algorithmen, Optimierung und Assembler - Algorothmus zum strecken bzw stauchen vom rechteck


gandalf ftw - Mo 29.10.07 18:11
Titel: Algorothmus zum strecken bzw stauchen vom rechteck
Hi
Ich bräuchte Hilfe bei nem Algorithmus zum stauchen bzw strecken von einem rechteck.Ich hab leider kein plan und es wär cool wenn es jemand von euch hinbekommt.

thx schonma im vorraus


alzaimar - Mo 29.10.07 18:20

Öhm, was ist das Problem? Ein Rechteck bleibt doch ein Rechteck, wenn es gestaucht oder gestreckt wird (ja ja, bis zum erreichen der Singularität bzw. Unendlichkeit)


Kroko - Mo 29.10.07 18:27

vielleicht so, wenn es parallel zum Bildschirm liegt,

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
TRechteck = record
  P: TPoint; //linke untere Ecke
  Breite,
  Hoehe: Integer:
end;

procedure Zeichne(const ACanvas: TCanvas; const R: TRechteck);
begin
  with R do ACanvas.Rectangle(P.X,P.Y,P.X+Breite,P.Y-Hoehe);
end;

procedure Skaliere(var R: TRechteck; const AFaktor: Double);
begin
  with R do
  begin
    Breite := Round(Breite*AFaktor);
    Hoehe := Round(Hoehe*AFaktor);
  end;
end;


gandalf ftw - Mo 29.10.07 19:17

naja das problem liegt darin das ich das selbe rechteck strecken und stauchen soll und ehrlich gesagt null plan hab wie ich das machen soll.


TheAxeEffect - Mo 29.10.07 19:53

könntest du bitte deine frage klar formulieren:
willst du das rechteck GRAFISCH sichtbar machen, oder nur die seiten berechnen.
und könntest du uns deine der worte "stauchen" und "strecken" liefern. heißt das, dass der umfang erhalten bleibt, oder heißt es, dass die länge einer seite erhalten bleibt?
mfg,
simon


gandalf ftw - Mo 29.10.07 21:58

also inder aufgabenstellung steht das ich das rechteck stauchen bzw strecken soll wobei der faktor egal is.also nehme ich mal an das die lange bzw die breite verändert werden.das rechteck soll sichtbar gemacht werden.ich habs selber nochma versucht aber ich bekomms nich hin


Kroko - Di 30.10.07 06:17

Und was gefällt Dir an meiner Skalieren-Prozedur nicht? Sie staucht bei AFaktor<1 und streckt bei AFaktor>1, :roll:


gandalf ftw - Do 01.11.07 23:10

was heißt nich gefällt - ich suche nen kompletten algorithmus wenns geht damit ich ihn denn nachvollziehen kann.


delfiphan - Do 01.11.07 23:47

Deine Frage ist nicht ausreichend genau gestellt.


Kroko - Fr 02.11.07 07:37

user profile icongandalf ftw hat folgendes geschrieben:
was heißt nich gefällt - ich suche nen kompletten algorithmus wenns geht damit ich ihn denn nachvollziehen kann.

Sorry ich verstehe nur Bahnhof


jasocul - Fr 02.11.07 08:56

user profile icongandalf ftw hat folgendes geschrieben:
ich habs selber nochma versucht aber ich bekomms nich hin
Zeige mal, was Du überhaupt hinbekommen hast.
user profile icongandalf ftw hat folgendes geschrieben:
also inder aufgabenstellung steht...
user profile icongandalf ftw hat folgendes geschrieben:
ich suche nen kompletten algorithmus
Ich bezweifle übrigens, dass hier Jemand Deine Aufgaben für Dich löst.


jaenicke - Fr 02.11.07 10:49

user profile icongandalf ftw hat folgendes geschrieben:
was heißt nich gefällt - ich suche nen kompletten algorithmus wenns geht damit ich ihn denn nachvollziehen kann.
Das Wort heißt glaube ich nicht nachvollziehen sondern abschreiben^^.

Nein, im Ernst:
Wie user profile iconjasocul bereits geschrieben hat, wird hier keiner einfach eine komplette Lösung für deine Aufgabe hinschreiben.
Das ist in deinem Fall aber auch gar nicht möglich, weil man aus deinen "Äußerungen" rein gar nicht erkennen kann wie die Aufgabe eigentlich aussieht, d.h. was du eigentlich machen sollst...

Schließlich ist user profile iconKrokos Antwort ja ein vollständiger Algorithmus, der genau das macht, was aus deinen Posts zu erkennen war. Das ist allerdings kein fertiges Programm zum Abpinseln und Abgeben ohne etwas selbst dafür zu tun. Und damit komme ich wieder auf den Anfang meines Posts zurück...

Ohne, dass du mal schreibst, was deine Versuche ergeben habe (als Quelltext), und weitere Informationen postest was du eigentlich genau machen sollst, wenn user profile iconKrokos Vorschlag nicht das ist, was du meinst, kann niemand dir helfen.


gandalf ftw - Fr 02.11.07 17:46

also ich habs jetzt gescahfft ein rechteck erstma zu programmieren mit penpos und lineto etc. nun versuche ich den streck bzw stauchfaktor in einem edit feld einzugeben um mein vorgezeichnetes rechteck zu stauchen.


jaenicke - Fr 02.11.07 19:16

user profile iconKroko hat dir doch bereits eine Lösung gepostet... Es gibt schon einen Befehl um ein Rechteck zu zeichnen, und den hat er auch verwendet. Auch das Strecken und Stauchen hat er bereits fertig gepostet.

Also warum benutzt du nicht einfach die Lösung?
Denn Fragen hast du zu der Lösung ja offensichtlich nicht, denn wenn dir der Quelltext nicht klar wäre, dann hättest du ja sicher gefragt, was die Befehle, die du nicht verstehst, bedeuten etc.


gandalf ftw - So 04.11.07 11:34

sowie ich das jetzt verstehe muss ich für breite und höhe jeweils x bzw nen y wert oben einsetzen oder bin ich da falsch


jaenicke - So 04.11.07 11:55

Du machst eine Variable vom Typ TRechteck, weist dann die einzelnen Werte zu und kannst dann die Methoden Zeichne und Skaliere aufrufen. Wobei Skaliere dann eben als zweiten Parameter den Wert erwartet, um den gestaucht oder gestreckt werden soll. 2.0 zum Beispiel für doppelte Größe.
Und Zeichne erwartet auch noch den Parameter wohin es gezeichnet werden soll, zum Beispiel den Canvas deines Formulars.

So ungefähr würde das aussehen (nein, mehr schreibe ich da nicht hin, da versuch erstmal selbst was und poste, was du versucht hast):

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:
type
  TRechteck = record
  {...}

  TForm1 = class
  { ...}

implementation

procedure Zeichne(const ACanvas: TCanvas; const R: TRechteck);
begin
{...}

procedure TForm1.Button1Click(Sender: TObject);
var
  // Variable vom Typ TRechteck deklarieren
begin
  Variable.P.X := {Wert};
  { andere Werte initialisieren...}

  Skaliere( , ); // Da fehlen natürlich noch die Parameter
  Zeichne( , );
end;
Statt TForm1.Button1Click kann da auch ein bisschen was anderes stehen, je nachdem wieviele Buttons du hast und wie dein Formular heißt.

Dass es dir vielleicht nicht ganz klar ist, wie man mit Records arbeitet, kann ich noch nachvollziehen, nicht allerdings, warum du das nicht nachliest.
Aber mit dem was ich gerade gepostet habe, musst du jetzt erstmal was machen. Mehr werde ich definitiv nicht schreiben ohne gepostete Versuche in Quelltextform von dir. Jetzt weißt du wo was hingehört (was ich bei einem Anfänger ja nicht gerade voraussetzen kann), und jetzt versuch damit erstmal was zu machen.

Wenn du dann Quelltext postest, wie du es versucht hast, dann können wir dir auch erklären, warum was so nicht geht.
Der Crashkurs von Christan [http://crashkurs.christian-stelzmann.de] hilft dir ja vielleicht auch.


gandalf ftw - So 04.11.07 14:44

ich schick euch meinen quelltext morgen, da hab ich schon ein rechteck gezeichnet.habs schon inner schule gemacht und der quelltext is aufm schulrechner


gandalf ftw - Mo 05.11.07 12:03


Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
procedure TForm1.FormCreate(Sender: TObject);
var X,Y:integer;
    P:TPoint;
begin
  X:=100;
  Y:=100;
  P.x:=100;
  P.y:=200;
  with Image1.Canvas do
  begin
  penpos:=P;
lineto(x,y);
lineto(x+200,y);
lineto(x+200,y+100);
lineto(x,y+100);
end;end;

end.


so habich mien rechteck gezeihnet. jetztmuss ich irgendwie ein edit feld einlesen lassen wo icheinenfaktor eingeben kann mit dem man das rechteck stauchen kann. geht das mit demwasihr mir geschrieben habt?

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


Kroko - Mo 05.11.07 12:24

user profile icongandalf ftw hat folgendes geschrieben:
procedure TForm1.FormCreate(Sender: TObject);

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
var X,Y:integer;
    P:TPoint;
begin
  X:=100;
  Y:=100;
  P.x:=100;
  P.y:=200;
  with Image1.Canvas do
  begin
  penpos:=P;
lineto(x,y);
lineto(x+200,y);
lineto(x+200,y+100);
lineto(x,y+100);
end;end;

end.
Sieht doch gleich viel besser aus, Code-Tags verwenden, :wink:
P kannst Du dir sparen, nimm statt PenPos einfach MoveTo(X,Y);

user profile icongandalf ftw hat folgendes geschrieben:
so habich mien rechteck gezeihnet. jetztmuss ich irgendwie ein edit feld einlesen lassen wo icheinenfaktor eingeben kann mit dem man das rechteck stauchen kann.
Einfach ein TEdit aufs Formular und mit StringToFloat auswerten, und 200*ScaleFactor und die 100*ScaleFactor

user profile icongandalf ftw hat folgendes geschrieben:
geht das mit demwasihr mir geschrieben habt?

Nein, deswegen habe ich es ja so gepostet


gandalf ftw - Mi 07.11.07 20:23

maht das nen unterschied ob ich das so wie du mache oder so wie ich?
so ich hab ma versucht das rechtekt durch nen faktor zu vergrößern bzw zu verkleinern - das problem is das der integer werte nicht mit extended werten auskommt und ob ihr da ne lösung für habt.


Kroko - Mi 07.11.07 20:37

ja, in schau mal in meinem ersten Beitrag wie ich Breite und Höhe berechne, gibt das Wort ein und drücke die Taste F1


gandalf ftw - Do 08.11.07 17:15

bei deinem haste ja geschrieben faktor: double - wie bekomm ich das hin das man da nen beliebigen faktor per edit feld eingeben kann?
ich habs ma versucht in dem ich da ne variable hintersetze aber denn zeigt er mir an integer und extend nich vereinbar oder sowas


Kroko - Do 08.11.07 17:18


Delphi-Quelltext
1:
2:
var Faktor: Double;
Faktor := FloatToStr(Edit1.Text);


gandalf ftw - Do 08.11.07 17:26


Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
procedure TForm1.Button1Click(Sender: TObject);
var X,Y:integer;
    P:TPoint;
    a,b:double;

begin
  a:=floattostr(Edit1.text);
  X:=100;
  Y:=100;
  P.x:=100;
  P.y:=200;
  with Image1.Canvas do
  begin
  penpos:=P;
  h:=200*a;
  g:=100*b
lineto(x,y);
lineto(x+a,y);
lineto(x+a,y+b);
lineto(x,y+b);
end;end;



so sieht mein button jetzt aus aber da steht es gibt keine überladene version von float to str

Moderiert von user profile iconjasocul: Delphi-Tags hinzugefügt


Kroko - Do 08.11.07 18:54

(a) b düfte in undefiniert sein
(b) Welche Delphi-Version?


Shorty - Do 08.11.07 20:51

user profile icongandalf ftw hat folgendes geschrieben:

Delphi-Quelltext
1:
a:=floattostr(Edit1.text);                    

Da sitzt der Fehler, du möchtest einen String in eine Fließkommazahl umwnadeln, deswegen brauchst du das so machen:

Delphi-Quelltext
1:
a:= StrToFloat(Edit1.Text)                    

Die Fehlermeldung, dass es keine überladene Version gibt, folgt daraus, dass du eine Methode mit falschen Parametern aufruft und Delphi eine überladene Methode mit genau diesen Parametern nicht findet.

MfG Shorty


Kroko - Do 08.11.07 20:52

mein Fehler, :oops:


Herr Bananerama - Fr 09.11.07 00:44

Du musst das noch runden, beispielweise mit round oder einfach StrToInt benutzen.

Übrigens ... ich würde nicht moveto und linto benutzen sonder Canvas.Rectangle. Ist dann kürzer und es ergibt in jedem Fall ein rechteck. Außerdem kann man das ausmahlen und TRects übergeben ;)

Deine version läuft auch, bzw. wirst du sehen wenn du es compilierst


gandalf ftw - Fr 09.11.07 16:05

der zeigt mir trotzdem integer und extendend sind inkompatible typen


Jakob_Ullmann - Fr 09.11.07 16:22

das ist klar. einen integer kannst du problemlos für ein Extended verwenden (da jede Ganzzahl auch eine rationale Zahl ist). Andersrum geht es logischerweise nicht. Du könntest höchstens den Wert auf eine Ganzzahl runden (mir round) oder alle Kommastellen abschneiden (mit trunc). Im Übrigen denke ich, dass mit der Aufgabe das Stauchen / Skalieren einer Rechteckigen Grafik gemeint ist.


jaenicke - Fr 09.11.07 16:24

user profile icongandalf ftw hat folgendes geschrieben:
der zeigt mir trotzdem integer und extendend sind inkompatible typen
Wenn etwas nicht funktioniert, dann poste doch bitte jeweils deinen Quelltext, die genaue Fehlermeldung (in diesem Fall hast du das ja) und in welcher Zeile des geposteten Quelltext der Fehler auftritt.
Das kürzt das ganze hier erheblich ab...


Kroko - Sa 10.11.07 18:00

Zitat:
vielleicht so, wenn es parallel zum Bildschirm liegt,

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
TRechteck = record
  P: TPoint; //linke untere Ecke
  Breite,
  Hoehe: Integer:
end;

procedure Zeichne(const ACanvas: TCanvas; const R: TRechteck);
begin
  with R do ACanvas.Rectangle(P.X,P.Y,P.X+Breite,P.Y-Hoehe);
end;

procedure Skaliere(var R: TRechteck; const AFaktor: Double);
begin
  with R do
  begin
    Breite := Round(Breite*AFaktor);
    Hoehe := Round(Hoehe*AFaktor);
  end;
end;

Kann es sein, dass uns user profile icongandalf ftw auf den Arm nehmen will :?:


tommie-lie - Sa 10.11.07 18:36

user profile iconKroko hat folgendes geschrieben:
Kann es sein, dass uns user profile icongandalf ftw auf den Arm nehmen will :?:
Kann es sein, daß er seit... wann hat das Schuljahr angefangen? 3 Monaten? ...einmal pro Woche 90 Minuten Informatikunterricht hat und wie so viele Informatikschüler keine sinnvolle Einführung in die IDE gekriegt hat und einfach nicht weiß, wie man mit der Kontexthilfe und den Fehlermeldungen richtig umgeht und ihm nie jemand richtig erklärt hat, was der Unterschied zwischen den verschiedenen Datentypen ist und wie und vor allem warum man sie korrekt ineinander überführen kann bzw muss und er einfach deinen vorgekauten Code nicht verstehen kann, weil ihm grundlegendes Wissen über Computertechnik und Programmierung fehlt?
Und nein, "da musst du round() verwenden, weil das ein Float ist" ist keine sinnvolle Erklärung.


@gandalf ftw:
Heutige Programmiersprachen unterscheiden in der Regel zwischen zwei grundlegenden Zahlenformaten, Fließkommazahlen und Ganzzahlen. Letztere sind die ganzen oder natürlichen Zahlen, wie du sie aus dem Matheunterricht kennst, erstere sind ein Teil der reellen Zahlen. Float, Single, Double, Extended sind allesamt Fließkommazahlen und unterscheiden sich lediglich in ihrer Genauigkeit (da der Computer nicht wirklich alle reellen Zahlen speichern kann, sind die Fließkommazahlen in der Computertechnik lediglich Näherungen). Integer, Byte, Short, und so weiter sind Ganzzahlen, die sich wiederum durch ihren Definitionsbereich (Integer zum Beispiel von rund -2 Milliarden bis +2 Milliarden) oder durch ihre Vorzeichenbehaftung (Integer kann auch negative Werte darstellen, Cardinal nicht) unterscheiden.
Um in der Mathematik aus einer reellen Zahl eine ganze Zahl zu machen, musst du wissen, wie du -5,312 als ganze zahl darstellen sollst. Das erwartete Ergebnis wäre -5, der Vorgang heißt runden. In Delphi übernimmt das die Funktion round(), der du als Parameter eine Fließkommazahl übergeben kannst und die als Rückgabewert eine Ganzzahl zurückliefert. Delphi kann diese Umwandlung nicht automatisch, da in einem Computer Fließkommazahlen und Ganzzahlen sehr unterschiedlich gespeichert werden. Das heißt überall, wo du zum Beispiel einen Integer erwartest, aber einen Double hast, musst du selbst die round-Funktion verwenden, um die Fließkommazahl zu runden.
Dann gibt es in Delphi als dritten grundlegenden Datentypen noch den String, der Zeichen enthält. Zur Umwandlung von Zahlenformaten in Strings und umgekehrt stehen 4 Funktionen zur Verfügung, IntToStr(), FloatToStr(), StrToInt() und StrToFloat(). Die Bedeutung dieser Funktionen sollte dir aus dem Englischunterricht klar sein, FloatToStr konvertiert Fließkommazahlen zu einem String.

Zu deinem Code: Wenn du bei deinem Code weißt, was du da tust und warum du es tust, lass dir auf keinen Fall sagen, daß eine andere Methode, die du nicht kennst, besser sei. Solange du noch lernst, ist die einzig richtige Lösung diejenige, die du auch verstehst und nachvollziehen kannst. Wenn du mit deinen 4 LineTo()s also zufrieden bist, ändere nichts daran. Woran du allerdings etwas ändern kannst, ist die Strukturierung deines Codes. Fällt dir auf, daß du jeweils zweimal 100 und 200 auf x oder y hinzuaddierst in deinen LineTo-Befehlen? Was bedeuten die 100 und 200 in diesem Fall konkret? Fallen die Variablennamen ein, die du statt der zwei Zahlen nehmen könntest? Wenn du diese Variablen statt der Zahlen nimmst, kannst du den Variablen andere Werte zuweisen und musst nicht jedesmal alle Vorkommen von 100 und 200 finden und ersetzen. Was passiert nun mit den beiden Werten, wenn das Rechteck doppelt so hoch oder doppelt so breit werden soll? Was musst du tun, um eine Zahl zu verdoppeln? Was um sie zu halbieren?

HTH


Kroko - Sa 10.11.07 20:18

user profile icontommie-lie hat folgendes geschrieben:
user profile iconKroko hat folgendes geschrieben:
Kann es sein, dass uns user profile icongandalf ftw auf den Arm nehmen will :?:
Kann es sein, daß er seit... wann hat das Schuljahr angefangen? 3 Monaten? ...einmal pro Woche 90 Minuten Informatikunterricht hat und wie so viele Informatikschüler keine sinnvolle Einführung in die IDE gekriegt hat und einfach nicht weiß, wie man mit der Kontexthilfe und den Fehlermeldungen richtig umgeht und ihm nie jemand richtig erklärt hat, was der Unterschied zwischen den verschiedenen Datentypen ist und wie und vor allem warum man sie korrekt ineinander überführen kann bzw muss und er einfach deinen vorgekauten Code nicht verstehen kann, weil ihm grundlegendes Wissen über Computertechnik und Programmierung fehlt?
Und nein, "da musst du round() verwenden, weil das ein Float ist" ist keine sinnvolle Erklärung.
...

Da macht es sich jemand sehr einfach bzw.
Wenn der Hund nicht schwimmen kann, ist das Wasser schuld!


gandalf ftw - So 11.11.07 16:05

so wie ich das jetzt verstehe muss bzw kann ich also die +100 bzw +200 als eine variable machen und die denn einsetzen oder? denn kann ich die mal den faktor nehmen wobei ich bei dem faktor den wert noch runden muss. bin ich jetzt so halbwegs richtig?


tommie-lie - So 11.11.07 16:15

user profile icongandalf ftw hat folgendes geschrieben:
so wie ich das jetzt verstehe muss bzw kann ich also die +100 bzw +200 als eine variable machen und die denn einsetzen oder?
Ja, aber wie könnten diese beiden Variablen denn sinnvolerweise heißen?

gandalf ftw hat folgendes geschrieben:
bin ich jetzt so halbwegs richtig?
Ja.


gandalf ftw - Mo 12.11.07 19:44

also so zu sagen h:=200 und b:=100
und davor h:round und b: round oder wo muss der rundungs befehl rein


Kroko - Mo 12.11.07 19:46

Sorry, aber vergiss es oder lies mal meine Signatur, zweiter Teil!
[EDIT] Der erste Teil passt aber auch!