Sign in Join

Live chat for Free Pascal, Lazarus, Delphi and every Pascal programmer.

Mailing lists / fpc-pascal / 2010-03

When is AnsiString not a good substitute for string?

5 messages · 4 people · –

Reply by email Subscribe to this list Your subscription

Read-only archive. Use j and k to move between messages.

Frank Church

I recently posted a question about problems involving the use of string and AnsiString when converting a Delphi program. Are the some situations where substituting AnsiString for string will result in errors?

Does using {$mode delphi}, {H+} involve cases which might introduce hard to track errors?

From what I have read AnsiString is a pointer to a potentially

unlimited string, where as string has a maximum length of 255, and in a record structure may have a fixed length in a preallocated memory.

Is it also an issue in objects and classes?

If anyone could point me to the relevant docs I would be glad.

Frank Church ======================= http://devblog.brahmancreations.com
Jürgen Hestermann
to Frank Church
Show quoted text 5 lines
Frank Church schrieb: I recently posted a question about problems involving the use of string and AnsiString when converting a Delphi program. Are the some situations where substituting AnsiString for string will result in errors?

The string type is a generic type and can be ShortString or AnsiString (or other string types). A compiler switch then decides what type will be used.

AnsiString and ShortString are quite different. AnsiStrings are much more complex (and require more care when using them i.e. in records) but have a maximum length of 2 (or 4?) GB while ShortStrings are simpler (and therefore often faster) but limited to 255 bytes.

When switching from one to the other type you may need to have a close look on how the strings are used in the program. Maximum length can be an issue. AnsiStrings are pointers so Sizeof() gives back 4 bytes while for ShortStrings it is the (maximum) size of the string plus 1 length byte. There are lots of such differences that *may* be a problem but not neccessarily are in all cases.

There is also an (IMO) semantic logic error with AnsiStrings: Although they are pointers (pointing to the string) in most (but not all!) cases the compiler interprets them as the strings they points to. A := B is possible if A is a ShortString and B is an AnsiString (although A is not a pointer). It should have been A := B^ but Borland in their wise wisdom decided not to use this clear syntax. Though for low level routines like SizeOf and Fillchar it still uses the (correct) meaning of a pointer. So this may cause problems too.

Just check how both types are handled by the compiler and you will soon see where problems can arise.

For AnsiStrings see here: http://www.freepascal.org/docs-html/ref/refsu10.html

Jonas Maebe
to Jorge Aldo G. de F. Junior
Jorge Aldo G. de F. Junior wrote
actually, for most porpuses, ansistring is a lot faster than normal strings with size 255... you pass around 4 bytes instead of 256...

And on the downside the compiler inserts a lot of initialisation/finalisation and reference increment/decrement code for ansistrings (which use atomic operations and hence are fairly slow), and if you use var/out/const parameters then the compiler will also pass around pointers to shortstrings instead of copying them all the time.

Unless you are assigning long strings to each other all the time (or if your string parameters are all value parameters even though you don't change them), I don't think ansistrings are much if any faster than shortstrings. In fact, the compiler internally uses shortstrings instead of ansistrings in a lot of places exactly because of speed reasons.

Jonas

Jürgen Hestermann
to Jorge Aldo G. de F. Junior: actually, for most porpuses, ansistring is a lot faster than normal strings with size…
Jorge Aldo G. de F. Junior schrieb: actually, for most porpuses, ansistring is a lot faster than normal strings with size 255... you pass around 4 bytes instead of 256...

That would be only true if you have multiple variables pointing to the same string without changing each instance. I don't believe that this the majority of code. Why would you use multiple variables then? After assigning the value of an AnsiString to another AnsiString variable I *always* modify it. And then the whole data gets copied too plus additional overhead like increasing the reference counter.