stream - Delphi ReadStreamStr, WriteStreamStr implementation check -
i'm using these implementations found on post on so. when reading string in sometimes, readstreamstr puts in characters string. i'm posting implementation here have checked , approved, , if there fault, corrected.
function readstreamstr(stream: tstream): string; { returns string stream } var lenstr: integer; begin result := ''; { length of string } lenstr := readstreamint(stream); { set string memory } setlength(result, lenstr); { read characters } stream.read(result[1], lenstr); end; procedure writestreamstr(stream: tstream; str: string); { writes string stream } var strlen: integer; begin { length of string } strlen := bytelength(str); { write length of string } writestreamint(stream, strlen); if strlen > 0 { write characters } stream.write(str[1], strlen); end;
thank you.
the integer
written in front of characters number of bytes, readstreamstr()
interpreting number of characters instead. in d2007 , earlier, string
ansi, works fine. in d2009 , later, string
unicode, not work. assuming using d2009+, means readstreamstr()
allocating twice memory should be, filling in half of it, leave other half uninitialized. not taking sizeof(char)
account when reading (but bytelength()
when writing).
try this:
function readstreamstr(stream: tstream): string; { returns string stream } var lenstr: integer; leftover: array[0..sizeof(char)-1] of byte; begin result := ''; { length of string } lenstr := readstreamint(stream); { set string memory } setlength(result, lenstr div sizeof(char)); if lenstr > 0 begin { read characters } stream.readbuffer(result[1], lenstr); { in case length not } lenstr := lenstr mod sizeof(char); if lenstr > 0 stream.readbuffer(leftover[0], lenstr); end; end;
alternatively:
function readstreamstr(stream: tstream): string; { returns string stream } var lenstr: integer; buf: tbytes; begin result := ''; { length of string } lenstr := readstreamint(stream); if lenstr > 0 begin { memory } setlength(buf, lenstr); { read characters } stream.readbuffer(buf[1], lenstr); { convert string } result := tencoding.unicode.getstring(buf); end; end;
either way, keep in mind if stream data written in d2007 or earlier, read in d2009 or later, code not work as-is. have go tbytes
approach, use more appropriate tencoding
decoding, such tencoding.default
.
personally, have opted instead read/write strings utf-8 beginning:
function readstreamstr(stream: tstream): utf8string; { returns string stream } var lenstr: integer; begin result := ''; { length of string } lenstr := readstreamint(stream); { set string memory } setlength(result, lenstr); if lenstr > 0 { read characters } stream.read(pansichar(result)^, lenstr); end; procedure writestreamstr(stream: tstream; const str: utf8tring); { writes string stream } var strlen: integer; begin { length of string } strlen := length(str); { write length of string } writestreamint(stream, strlen); if strlen > 0 { write characters } stream.write(pansichar(str)^, strlen); end;
Comments
Post a Comment