Entwickler-Ecke
Algorithmen, Optimierung und Assembler - File einlesen als Integer Werte
cassah - Mi 06.07.05 19:58
Titel: File einlesen als Integer Werte
Hallo,
ich habe folgendes Problem:
ich will eine Topography Datei einlesen, von der
die Spalten- sowie Zeilenanzahl der einzelnen Werte bekannt ist (X und Y).
Das Format der Datei ist little-endian und die einzelnen Werte sind
16-bit signed integer. soweit so gut. ich habe das file bereits im speicher:
Delphi-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20:
| var iFileLength : Integer; iBytesRead : Integer; Buffer : PChar; fileName,f : String;
begin f := FileOpen(fileName, fmOpenRead);
if (f>0) then begin iFileLength := FileSeek(f,0,2); FileSeek(f,0,0); Buffer := PChar(AllocMem(f + 1)); iBytesRead := FileRead(f, Buffer^, iFileLength);
FileClose(f); end; end; |
Nun will ich über 2 ineinanderliegende Schleifen (Y und X)
die einzelnen 16 bit signed integer aus dem buffer auslesen,
und in einem TImage einen Farbwert entsprechend der größe
des Wertes setzen (Höhenmodell).
Damit bin ich aber leider überfordert. Hab schon einiges probiert,
aber Typecasting ist scheinbar nicht das Zauberwort :(
Hat jemand ein paar ideen?
Vielleicht auch zu dem Problem, wie ich die Integer Werte dann in
den Typ TColor umwandeln kann (Shifting?)
Danke erstmal.
Eric
Moderiert von
raziel: Code- durch Delphi-Tags ersetzt.
maxk - Mi 06.07.05 23:50
Hallo und :welcome: im DF,
ich verstehe leider nicht so richtig, wo genau dein Problem liegt. Womit kommst du den nicht klar - mit dem Auslesen der Werte oder mit der Darstellung? Ich muss auch zugeben mit little-endian nichts anfangen zu können und was ich gerade im Netz gefunden habe scheint nicht das zu sein, was du da hast. Wie ist die Datei denn aufgebaut?
Zitat: |
Hat jemand ein paar ideen?
Vielleicht auch zu dem Problem, wie ich die Integer Werte dann in
den Typ TColor umwandeln kann (Shifting?) |
Wie stellst du dir denn die Farben vor? Soll jeder Wertebereich eine eigene Farbe erhalten oder soll die Farbe entsprechend des Wertes "verlaufen"?
Gruß,
maxk
cassah - Do 07.07.05 00:07
Also meinen Recherchen nach ist little endian die Ablage der Bytes.
Da die Werte 16 bit lang sind, bestehen sie aus 2 chars. Diese sind
dann (bei little endian) verkehrt herum gespeichert:
Ist das Datenwort zum Beispiel vier Byte (also 32 Bit) lang, werden die vier Bytes (b0,b1,b2,b3) in einem "big endian" System im Speicher so angeordnet, wie man die Stellen einer Dezimalzahl auf Papier schreiben würde, also zuerst das höchstwertige Byte und zuletzt das Byte mit dem geringsten Stellenwert (b3,b2,b1,b0). Zuvorderst steht hier also das "big end". In "little endian"-Systemen hingegen steht das Byte mit dem niedrigsten Stellenwert am weitesten links und das Byte mit dem höchsten Stellenwert am weitesten rechts (b0,b1,b2,b3). Zuvorderst steht also das "little end".
Mein Problem ist nun, dass ich jede Menge chars im Ram hab, ich aber aus jeweils 2 chars einen integer "bauen" muss. wie geht sowas?
..und zu der frage mit den farben:
ich will einen farbverlauf erstellen. das heißt je höher der 16 bit wert ist, desto
heller soll die farbe sein. ideal wäre ein farbverlauf von weiß zu schwarz analog
zum bereich minimalwert <-> maximalwert. das problem ist
eher die umwandlung von 16 bit signed integers zum typ Tcolor.
ich hoffe das macht das problem ein wenig klarer.
so denn - Eric
Allesquarks - Do 07.07.05 01:03
Delphi's typecasting kann man im allgemeinen glaube ich nur über Zeiger umgehen. Wenn Du in der Delphi-Hilfe unter Zeigern nachschaust gibt es dazu auch irgendwo ein Beispiel.
Normalerweise brauchst Du erst einen allgemeinen Zeiger und danach einen spezialisierten
Delphi-Quelltext
1: 2: 3: 4: 5: 6: 7:
| var pointerallg:pointer;int16pointer:Pinteger^;myint:int16; begin pointerallg:=addr(Deinlitteendian); int16pointer:=pointerallg; myint16:=int16pointer^; end; |
Wie viele bytes er dann braucht entscheidet Delphi glaube ich selbst.
cassah - Fr 08.07.05 10:06
Hi,
problem gelöst. hier nun die Lösung:
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: 31: 32: 33: 34: 35: 36: 37: 38: 39:
| var pointerallg : Pointer; int16pointer : PSmallint; myint : Smallint; heightVal : Byte; col : TColor; Buffer : PChar; fileLength : Longint; begin for i:=0 to ((fileLength div 2) - 1) do begin pointerallg := addr(Buffer[i * 2]); int16pointer := pointerallg; myint := int16pointer^; heightVal := Byte(myint div 256);
col := RGBToColor(heightVal, heightVal, heightVal);
Image1.Canvas.Pixels[x, y] := col; end; end;
function TForm1.RGBToColor(R, G, B : byte): TColor; begin Result := ((R and $FF) shl 16) + ((G and $FF) shl 8) + (B and $FF); end; |
vielen Dank für die Hilfe!
Eric
Entwickler-Ecke.de based on phpBB
Copyright 2002 - 2011 by Tino Teuber, Copyright 2011 - 2025 by Christian Stelzmann Alle Rechte vorbehalten.
Alle Beiträge stammen von dritten Personen und dürfen geltendes Recht nicht verletzen.
Entwickler-Ecke und die zugehörigen Webseiten distanzieren sich ausdrücklich von Fremdinhalten jeglicher Art!