Chr(0) in String verketten und in File schreiben
Re: Chr(0) in String verketten und in File schreiben
Erst die Daten im Memory zusammenstellen (AllocateMemory)
Dann die Daten komplett schreiben (WriteData)
Dann die Daten komplett schreiben (WriteData)
Alles ist möglich, fragt sich nur wie...
Projekte ThreadToGUI / EventDesigner V3 / OOP-BaseClass-Modul
Downloads auf MyWebspace / OneDrive
Projekte ThreadToGUI / EventDesigner V3 / OOP-BaseClass-Modul
Downloads auf MyWebspace / OneDrive
Re: Chr(0) in String verketten und in File schreiben
8 MB Byte für Byte zu schreiben ist nicht das Problem.
Die Stringfunktion Mid() ist zu langsam!
(PureBasic weiß nicht, wie lang ein String ist und liest deshalb bei jedem Aufruf von Mid() den String von Anfang an bis zur Startposition. Könnte ja sein, daß der String kürzer ist als die angegebene Startposition)
Tausche ich Mid() gegen PeekS(), geht es flott.
Eine andere Alternative wäre ein Pointer mit Struktur, mit dem man durch den String läuft.
Geschwindigkeitstest:
Die Stringfunktion Mid() ist zu langsam!
(PureBasic weiß nicht, wie lang ein String ist und liest deshalb bei jedem Aufruf von Mid() den String von Anfang an bis zur Startposition. Könnte ja sein, daß der String kürzer ist als die angegebene Startposition)
Tausche ich Mid() gegen PeekS(), geht es flott.
Eine andere Alternative wäre ein Pointer mit Struktur, mit dem man durch den String läuft.
Geschwindigkeitstest:
Code: Alles auswählen
OpenConsole()
a$ = "001122AABBCCDDEEFF" ; Teststring
Repeat
a$ + a$ ; Teststring verlängern
Until Len(a$) > 8000000 ; bis über 8 MB
lenght = Len(a$)
t = ElapsedMilliseconds()
For i = 1 To lenght Step 2
;b$ = Mid(a$, i, 2) ; < - Langsam
b$ = PeekS(@a$ + (i - 1) * SizeOf(character), 2) ; < - Schneller
;byte = Val("$" +b$)
; Kontrollausgabe, wie schnell die Schleife läuft
If i % 10000 = 1
PrintN("Fortschritt: " + Str(i))
EndIf
Next i
PrintN("Zeit: " + Str(ElapsedMilliseconds() - t))
Input()
- NicTheQuick
- Ein Admin
- Beiträge: 8679
- Registriert: 29.08.2004 20:20
- Computerausstattung: Ryzen 7 5800X, 32 GB DDR4-3200
Ubuntu 22.04.3 LTS
GeForce RTX 3080 Ti - Wohnort: Saarbrücken
- Kontaktdaten:
Re: Chr(0) in String verketten und in File schreiben
Ich hätte hier noch eine Funktion, die aus einem Unicode-String, der aus Hexzeichen besteht einen Speicherbereich erzeugt mit dem dekodierten Inhalt. Allerdings überprüft er nicht, ob gültige Hexzeichen benutzt werden. Der Prototyp ist nur dazu da, damit man Strings ohne @ übergeben kann, er aber trotzdem nicht kopiert, sondern nur per Referenz weitergegeben wird.
Der Speicherpuffer beginnt mit einer festgelegten Größe (1024) und wird immer wieder verdoppelt, falls nicht mehr alles reinpasst. Das ist ein übliches Verfahren für dynamische zusammenhängende Speicherbereiche.
Am Ende sollte man daran denken den Speicherbereich wieder mit FreeMemory() freizugeben.
Der Speicherpuffer beginnt mit einer festgelegten Größe (1024) und wird immer wieder verdoppelt, falls nicht mehr alles reinpasst. Das ist ein übliches Verfahren für dynamische zusammenhängende Speicherbereiche.
Am Ende sollte man daran denken den Speicherbereich wieder mit FreeMemory() freizugeben.
Code: Alles auswählen
Prototype.i hex2bin(input.p-unicode)
Procedure.i __hex2bin(*input)
Protected *i.Character = *input
Protected bufSize.i = 1024
Protected *buf = AllocateMemory(bufSize)
Protected *bufEnd = *buf + bufSize
Protected *bufTmp
Protected *o.Ascii = *buf
Protected state.i = 0
Protected digit.i
While *i\c
If *i\c <= '9'
digit = *i\c - '0'
Else
digit = (*i\c & $1f) + 9
EndIf
If state = 0
*o\a = digit << 4
state = 1
Else
*o\a | digit
state = 0
*o + 1
If *o = *bufEnd
*bufTmp = ReAllocateMemory(*buf, bufSize * 2)
If Not *bufTmp
FreeMemory(*buf)
ProcedureReturn #False
EndIf
*buf = *bufTmp
*o = *buf + bufSize
bufSize * 2
*bufEnd = *buf + bufSize
EndIf
EndIf
*i + SizeOf(Character)
Wend
If *o - *buf = 0
ProcedureReturn #False
EndIf
*bufTmp = ReAllocateMemory(*buf, *o - *buf)
If Not *bufTmp
FreeMemory(*buf)
ProcedureReturn #False
EndIf
ProcedureReturn *bufTmp
EndProcedure
Global hex2bin.hex2bin = @__hex2bin()
s.s = "57696c6c6b6f6d6d656e20696d20507572652d426f61726400"
*a = hex2bin(s)
Debug PeekS(*a, -1, #PB_Ascii)
FreeMemory(*a)
Re: Chr(0) in String verketten und in File schreiben
Hab mal ne lib in fasm gebastelt eventuell besteht ja Interesse
Der Code funktioniert nur wenn der Hex-String intakt ist also keine ungültigen Zeichen enthält
und es müssen immer 2 Character Paare (Groß) pro Byte vorliegen.
Download:
https://www.dropbox.com/s/5242otg3qtg3o ... 4.zip?dl=0
Der Code funktioniert nur wenn der Hex-String intakt ist also keine ungültigen Zeichen enthält
und es müssen immer 2 Character Paare (Groß) pro Byte vorliegen.
Code: Alles auswählen
EnableExplicit
;Windows x64 Unicode (uppercase) only!
Import "h2b.lib"
h2bConvert.i(*Str)
h2bSize.i(*Buffer)
h2bFree.i(*Buffer)
EndImport
Global teststring.s
Global *buffer
teststring = "FF00FF"
*buffer = h2bConvert(@teststring)
ShowMemoryViewer(*buffer,3)
Debug h2bSize(*buffer)
Debug h2bFree(*buffer)
End
https://www.dropbox.com/s/5242otg3qtg3o ... 4.zip?dl=0
- NicTheQuick
- Ein Admin
- Beiträge: 8679
- Registriert: 29.08.2004 20:20
- Computerausstattung: Ryzen 7 5800X, 32 GB DDR4-3200
Ubuntu 22.04.3 LTS
GeForce RTX 3080 Ti - Wohnort: Saarbrücken
- Kontaktdaten:
Re: Chr(0) in String verketten und in File schreiben
Wieso eigentlich als Library? Wäre es nicht einfacher das direkt in Inline-ASM zu machen?
Re: Chr(0) in String verketten und in File schreiben
Ginge schon aber umständlicher und mit mehr Code.NicTheQuick hat geschrieben:Wieso eigentlich als Library? Wäre es nicht einfacher das direkt in Inline-ASM zu machen?
Keine Freiheiten/Krontrolle im Funktionsaufbau -> man muss dann mit dem Setup von Procedure arbeiten/leben...
Wenn es nur eine ProcedureASM.i () geben würde wo man volle Kontrolle hätte.
-
- Beiträge: 23
- Registriert: 14.12.2018 23:01
Re: Chr(0) in String verketten und in File schreiben
Hallo Gemeinde!
Vielen Dank für eure Arbeit, Tips und Anregungen. Hab das Problem jetzt relativ einfach lösen können,
in dem ich mit der Funktion getdatabaseblob die Binärdaten aus der DB2 DB direkt in den Speicher lese
und von da in eine Datei schreiben kann. Geht auch vertretbar schnell. Je nachdem wie groß (Movie) so ein
Blob halt ist.
Hier der Code:
Vielen Dank für eure Arbeit, Tips und Anregungen. Hab das Problem jetzt relativ einfach lösen können,
in dem ich mit der Funktion getdatabaseblob die Binärdaten aus der DB2 DB direkt in den Speicher lese
und von da in eine Datei schreiben kann. Geht auch vertretbar schnell. Je nachdem wie groß (Movie) so ein
Blob halt ist.
Hier der Code:
Code: Alles auswählen
If DatabaseQuery(0, insql$, #PB_Database_StaticCursor)
NextDatabaseRow(0)
collen = DatabaseColumnSize(0,0)
*MemoryID = AllocateMemory(collen)
GetDatabaseBlob(0,0,*MemoryID,collen)
If *MemoryID
OpenFile(0,dsname$)
WriteData(0,*MemoryID,collen)
CloseFile(0)
FreeMemory(*MemoryID)
EndIf
EndIf
- NicTheQuick
- Ein Admin
- Beiträge: 8679
- Registriert: 29.08.2004 20:20
- Computerausstattung: Ryzen 7 5800X, 32 GB DDR4-3200
Ubuntu 22.04.3 LTS
GeForce RTX 3080 Ti - Wohnort: Saarbrücken
- Kontaktdaten:
Re: Chr(0) in String verketten und in File schreiben
Und wir denken die ganze Zeit dieser Blob besteht aus Hexadezimaldaten. Wieso hast du nicht gleich gesagt, dass das ein binärer Blob ist?
-
- Beiträge: 23
- Registriert: 14.12.2018 23:01
Re: Chr(0) in String verketten und in File schreiben
Sorry! Hatte zuerst mit GetDatabaseString probiert,da kamen die Daten in Hex zurück. Erst bei
größeren BLOBs gab es dann Probleme.
Jetzt tut.
Sorry nochmal. War da auf dem Holzweg.
Habe aber wieder was dazu gelernt.
LG
Jörg
größeren BLOBs gab es dann Probleme.
Jetzt tut.
Sorry nochmal. War da auf dem Holzweg.
Habe aber wieder was dazu gelernt.
LG
Jörg
- NicTheQuick
- Ein Admin
- Beiträge: 8679
- Registriert: 29.08.2004 20:20
- Computerausstattung: Ryzen 7 5800X, 32 GB DDR4-3200
Ubuntu 22.04.3 LTS
GeForce RTX 3080 Ti - Wohnort: Saarbrücken
- Kontaktdaten: