MichaelHooker
Programmer
This one has me baffled. I use Delphi 7 Personal Edition.
The Delphi Help says of IndexOfName:
"Returns the position of the first name-value pair with the specified name.
...
Call IndexOfName to locate the first occurrence of a name-value pair where the name part is equal to the Name parameter or differs only in case. IndexOfName returns the 0-based index of the string. If no string in the list has the indicated name, IndexOfName returns -1.
Note: If there is more than one name-value pair with a name portion matching the Name parameter, IndexOfName returns the position of the first such string."
Note the use of the word "first". The .Values function is supposed to work the same way.
I have written a routine using IndexOfName to pick items out of a name-value list. As an item is matched up the relevant name-value pair is removed from the list, so as to leave a list of un-matched items. It works perfectly when the names are unique but when they are not it does not behave as the Help suggests (which is what I need). IndexOfName is returning the position of the <second> matching name, not the first, and .Values also returns the value of the second instance of the name.
This is the relevant part of the routine, which is called from a for loop cycling through a list of search targets:
This is a few lines of TempList
I guess I can get around this by checking whether or not the name previous to the found name is the same and if so fetching the value of that previous entry in the list, or by sorting the list backwards (by sending the lines in reverse order into a temporary StringList and swapping them back to TempList again). But (a) it's going to slow things down (b) I don't yet know what's going to happen if there are more than two names the same and (c) it shouldn't be necessary, should it?
So my question is: have I completely misunderstood the Help, am I doing something stupid or is it just that Delphi doesn't work as advertised?
Thanks.
Michael Hooker
The Delphi Help says of IndexOfName:
"Returns the position of the first name-value pair with the specified name.
...
Call IndexOfName to locate the first occurrence of a name-value pair where the name part is equal to the Name parameter or differs only in case. IndexOfName returns the 0-based index of the string. If no string in the list has the indicated name, IndexOfName returns -1.
Note: If there is more than one name-value pair with a name portion matching the Name parameter, IndexOfName returns the position of the first such string."
Note the use of the word "first". The .Values function is supposed to work the same way.
I have written a routine using IndexOfName to pick items out of a name-value list. As an item is matched up the relevant name-value pair is removed from the list, so as to leave a list of un-matched items. It works perfectly when the names are unique but when they are not it does not behave as the Help suggests (which is what I need). IndexOfName is returning the position of the <second> matching name, not the first, and .Values also returns the value of the second instance of the name.
This is the relevant part of the routine, which is called from a for loop cycling through a list of search targets:
Code:
{Target is the string to be matched with a name;
TempList is the StringList of Name-Value pairs to be searched;
Position is the position in TempList returned by IndexOfName;
OutLine is the value part of a match;
ProcessOutLine is a separate procedure which processes Outline.}
Position := TempList.IndexOfName(Target);
if Position > - 1 then begin
OutLine.CommaText := TempList.Values[Target];
//OutLine.CommaText := TempList.ValueFromIndex[Position]; alternative to line above
ProcessOutLine;
TempList.Delete(Position);
end
{else... do something else if Position = -1, ie Target wasn't found}
This is a few lines of TempList
The first search for 'QFA2' as Target returns the second instance, asterisked above. That line is then deleted and the second search for 'QFA2' returns the remaining instance, which happens to be the first one. So they come out the wrong way round. This happens whether or not TempList has been sorted, the natural order and the sorted order both happen to place the target Names in the "right" order. And it all matters because Target is just one field in another CommaText StringList, and the object of the exercise is to combine the two sets of data fields relating to Target.PIA786=PIA786,1930,B773,OPRN,27L,DVR4G
PIA788=PIA788,1650,B772,OPKC,27L,DVR4G
QFA10=QFA10,2135,B744,WSSS,27L,BPK6G
QFA2=QFA2,0910,B744,VTBS,27R,BPK6F
QFA2=QFA2,2214,B744,VTBS,27L,BPK6G *
QFA30=QFA30,1220,B744,VHHH,27R,BPK6F
QFA32=QFA32,1219,B744,WSSS,27R,DVR5F
QTR002=QTR002,2113,A346,OTBD,27L,DVR4G
QTR008=QTR008,2152,A333,OTBD,27L,DVR4G
I guess I can get around this by checking whether or not the name previous to the found name is the same and if so fetching the value of that previous entry in the list, or by sorting the list backwards (by sending the lines in reverse order into a temporary StringList and swapping them back to TempList again). But (a) it's going to slow things down (b) I don't yet know what's going to happen if there are more than two names the same and (c) it shouldn't be necessary, should it?
So my question is: have I completely misunderstood the Help, am I doing something stupid or is it just that Delphi doesn't work as advertised?
Thanks.
Michael Hooker