17.6.1.2191 SEARCH STRING
Search the string specified by c-addr1 u1 for the string specified by c-addr2 u2. If flag is true, a match was found at c-addr3 with u3 characters remaining. If flag is false there was no match and c-addr3 is c-addr1 and u3 is u1.
Testing:
T{ : s3 S" jklmn" ; -> }T
T{ : s4 S" z" ; -> }T
T{ : s5 S" mnoq" ; -> }T
T{ : s6 S" 12345" ; -> }T
T{ : s7 S" " ; -> }T
T{ s1 s2 SEARCH -> s1 <TRUE> }T
T{ s1 s3 SEARCH -> s1 9 /STRING <TRUE> }T
T{ s1 s4 SEARCH -> s1 25 /STRING <TRUE> }T
T{ s1 s5 SEARCH -> s1 <FALSE> }T
T{ s1 s6 SEARCH -> s1 <FALSE> }T
T{ s1 s7 SEARCH -> s1 <TRUE> }T
ContributeContributions
JimPeterson [295] Possible Reference ImplementationSuggested reference implementation2023-04-09 18:50:46
This is the best I could come up with for this one:
: SEARCH {: c-addr1 u1 c-addr2 u2 -- c-addr3 u3 flag :}
c-addr1
u1 u2 - 1+ 0 MAX 0 ?DO \ only search up to u1-u2 characters
DUP u2 c-addr2 u2 COMPARE 0= IF
u1 I - TRUE UNLOOP EXIT \ u3 is u1 minus however far we scanned in
THEN
CHAR+
LOOP
DROP
c-addr1 u1 FALSE
;
The spec saying "... with u<sup>3 characters remaining." sounds a bit vague to me, but I took it to mean that c-addr3 u3 CHARS + c-addr1 u1 CHARS + =
, which is to say that c-addr<sup>3 u<sup>3 is the tail end of the c-addr<sup>1 u<sup>1 string, where c-addr<sup>3 u<sup>2 is the same string as c-addr<sup>2 u<sup>2 (when a match is found)
There is also no mention of whether or not the search proceeds forwards from c-addr<sup>1 or backwards from c-addr<sup>1+u<sup>1-u<sup>2, or what happens if c-addr<sup>2 u<sup>2 appears multiple times in c-addr<sup>1 u<sup>1. It should maybe say "... for the first occurrence of the string specified by c-addr<sup>2 u<sup>2."