Posted: 10th Jun 2007 22:56
Okay. I am creating a text parser function that will return a part of a string, which can be specified in the parameters. Each part is spearated by a "~".

Currently I am going through every letter, from the start, one by one and adding that letter to a text variable until I get to a "~". When I do, I increase the current part variable (it started at 1), clear the text variable, and do the same thing again. If the current part variable was equal to the part that I specified in the parameters at the time of the part variable increase (before I increased the variable that is...), then the text is added to the output variable before that text variable is cleared. After a match was found, the function exits and returns the output text variable.

Is there a faster way to get a certain "part" of a string of text, because when I'm looking for higher "parts" of a string the function can get REALLY slow...

Sorry if this makes absolutely no sense. I tried to explain it as best I could. If you need clarification just ask. Also, posting an example text parser may help as well...

Thanks,
-Sixty Squares.
Posted: 10th Jun 2007 23:07
I wrote a text parser function that does almost exactly that not too long ago. I will post it here when I get home [edit] Nevermind, go with IanM's utility, it's definitly faster[/edit], but I'm not sure how fast it is. If I understand what you need correctly (an example would help explain better by the way) it's a safe bet it's pretty fast. (It does caching too so if you need a different part of the previous string it will find it almost instantly.)
Posted: 10th Jun 2007 23:35
My utility plug-in 16 has 3 functions/commands that will do this very easily.

SPLIT STRING to take a string and split it into separate 'words' (delimited fields)
SPLIT COUNT() to retrieve the number of words/fields
and finally GET SPLIT WORD$() to retrieve each word/field

Alternatively, you can also use the INSTR function to locate the positions of all of the delimiters and the extended MID$ to extract the field in the same way that you are now, but faster.
Posted: 11th Jun 2007 3:58
@Code Dragon: Thanks for trying to help I'll check out IanM's plugin.

@IanM: I'll have to try your plugin One question about it though. Can it return what's inbetween symbols such as "<" and ">" and "[" and "]"?(including the symbols...)

Thanks again,
Sixty Squares
Posted: 11th Jun 2007 15:00
You can use the TRIM function to remove those characters from each end of your string, if that's what you mean. Or you can even use one of the REPLACE or REMOVE functions to do the same job.

If that doesn't answer what you are asking, give me an example of the input & output and I'll tell you what commands are best to use.
Posted: 11th Jun 2007 15:34
Okay: Here is what I mean:

Original Text
Hello.~My Name is <TEXT IN BRACKETS> Man.


Part one would be "Hello."

Part two would be the "My Name is "

Part 3 would be the <TEXT IN BRACKETS>

Part 4 would be the "Man."


*Retrieve "part" 3*

Output:
<TEXT IN BRACKETS>



If there any way to retrieve specific "parts" like that?
Posted: 11th Jun 2007 16:37
You might find what you are looking for here if you can't do it with Ian's plug-in.

http://forum.thegamecreators.com/?m=forum_view&t=102344&b=6

My string array functions are also there too - which includes an ArrayStr() function. With that, all you would need to do is check the resulting array for the one which starts with a '<' and extract the text between the angled brackets.

It's dead simple - and there's probably the same thing in Ians plug-in already.

TDK_Man
Posted: 11th Jun 2007 21:12
@Sixty Squares,

If your string was "Hello.~My Name is~<TEXT IN BRACKETS>~Man.", (each section is separated by ~) then the code is dead simple - here I split the string and look at each line in turn:
+ Code Snippet
InputLine  as string = "Hello.~My Name is~&lt;TEXT IN BRACKETS&gt;~Man."

split string InputLine, "~"

for Field = 1 to split count()
   print "Looking at field "; Field; " - ";
   if left$( get split word$(Field), 1 ) = "&lt;" and right$( get split word$(Field), 1 ) = "&gt;"
      print "It's an enclosed string - contents are "; trim$( get split word$(Field), "&lt;&gt;")
   else
      print "It's a normal string - value is "; get split word$(Field)
   endif
next


If the string you posted originally is actually what you want, then you need to work a little harder at the code:
+ Code Snippet
InputLine  as string = "Hello.~My Name is &lt;TEXT IN BRACKETS&gt; Man."

Field = 0
repeat
   inc Field
   Extract$ = GetField(InputLine, Field)

   if Extract$ &lt;&gt; ""
      print "Field "; Field; " - ";
      if left$(Extract$, 1) = "&lt;"
         print "It's an enclosed string - contents are "; trim$( Extract$, "&lt;&gt;")
      else
         print "It's a normal string - value is "; Extract$
      endif
   endif
until Extract$ = ""

print ""
print "Done"
wait key
end


function GetField(InputLine as string, WantedField as integer)
   local Field
   local SearchPos
   local EndPos
   local DL$

   DL$ = "~"
   Field = 0
   EndPos = 0
   repeat
      inc Field
      SearchPos = EndPos + 1
      EndPos = FindNextDelimiter( InputLine, "~&lt;&gt;", SearchPos )
      if EndPos = 0 then EndPos = len(InputLine)+1
   until Field = WantedField or EndPos &gt; len(InputLine)
   if Field = WantedField
      select mid$(InputLine, EndPos)
         case "&lt;"
            ` This delimiter is part of the next field
            dec EndPos
         endcase
         case "&gt;"
            ` This delimiter is part of the current field, so don't adjust endpos
            ` Check character prior to field to see if it should be included
            if SearchPos &gt; 1
               if mid$(InputLine, SearchPos - 1) = "&lt;" then dec SearchPos
            endif
         endcase
         case "~"
            dec EndPos
         endcase
      endselect
      exitfunction mid$( InputLine, SearchPos, EndPos - SearchPos + 1 )
   endif
endfunction ""

function FindNextDelimiter(InputString as string, Delimiters as string, StartPos as integer)
   local Pos
   local Found
   local i

   Pos = len(InputString) + 9999
   for i = 1 to len( Delimiters )
      Found = instr( InputString, mid$(Delimiters, i), StartPos )
      if Found &gt; 0 then Pos = min(Pos, Found)
   next
   if Pos &gt; len(InputString) then Pos = 0
endfunction Pos


This last one is a bit of a mess really. Anyway, it's given me one or two more ideas for new string functions to make this kind of parsing easier - thanks
Posted: 11th Jun 2007 21:51
The next release of the plug-ins will include at least one new function - The delimiters are now saved during the splitting of a string so that they can be retrieved later - that makes the code as easy to write as the first version:
+ Code Snippet
InputLine  as string = "Hello.~My Name is &lt;TEXT IN BRACKETS&gt; Man."

split string InputLine, "~&lt;&gt;"

for Field = 1 to split count()
   print "Looking at field "; Field; " - ";
   if get split delimiter$(Field-1) = "&lt;" and get split delimiter$(Field) = "&gt;"
      print "It's an enclosed string - contents are "; get split word$(Field)
   else
      print "It's a normal string - value is "; get split word$(Field)
   endif
next
Posted: 11th Jun 2007 22:15
@IanM: I'm glad I've sparked an idea for you to work on On any note, I believe that using your idea with putting the "~" around the brackets should make your idea 99% usable (there's that 1% failure chance... lol). Now all I need to do is fix my previous attempts

@TDK: The function I currenty have does something like that, but it uses the MID$() command and is really slow . I think I'm going to try IanM's plugin at the moment. Thanks though

EDIT: IanM's plugin in combination with Cloggy's D3D Plugin (and the reprogramming of the text system...) has solved the issues I was having with my game. Thanks for the help.