I'm a bit confused by this behaviour, and am unsure whether it needs to be better documented, or perhaps is a bug.
int main() { object buf = Stdio.Buffer("#44"); write("Matches: %O %O\n", buf->sscanf("#%2[4]"), (string)buf); buf = Stdio.Buffer("#4"); write("Doesn't: %O %O\n", buf->sscanf("#%2[4]"), (string)buf); buf = Stdio.Buffer("#44"); write("Matches: %O %O\n", buf->match("#%2[4]"), (string)buf); buf = Stdio.Buffer("#4"); write("Doesn't: %O %O\n", buf->match("#%2[4]"), (string)buf); }
When using sscanf, the successful match returns ({"44"}) and leaves the buffer empty, and the unsuccessful match returns an empty array and leaves the "4" in the buffer. This makes sense; the hash was matched and consumed, but the 2-character requirement meant that nothing was matched.
Using match instead produces a somewhat odd result though. If there's enough text in the buffer, it returns "44" and leaves the buffer empty; this corresponds to sscanf's behaviour. In the other case, though, it returns "#%2[4]" (the pattern), and leaves "4" in the buffer. Is this intentional?
(If the first character of the buffer isn't a hash, both return 0 and leave the buffer unchanged. This behaviour is also correct. It's only the partial match that seems curious.)
ChrisA
Hi Chris.
I'm a bit confused by this behaviour, and am unsure whether it needs to be better documented, or perhaps is a bug.
[...]
When using sscanf, the successful match returns ({"44"}) and leaves the buffer empty, and the unsuccessful match returns an empty array and leaves the "4" in the buffer. This makes sense; the hash was matched and consumed, but the 2-character requirement meant that nothing was matched.
Using match instead produces a somewhat odd result though. If there's enough text in the buffer, it returns "44" and leaves the buffer empty; this corresponds to sscanf's behaviour. In the other case, though, it returns "#%2[4]" (the pattern), and leaves "4" in the buffer. Is this intentional?
It did not appear to be intentional.
(If the first character of the buffer isn't a hash, both return 0 and leave the buffer unchanged. This behaviour is also correct. It's only the partial match that seems curious.)
Thanks for the report.
Fixed in Pike master. match() now returns "" in this case.
/grubba
Even more fun with match():
Stdio.Buffer("1 2-3")->match("%d%d%d");
(1) Result: 0
I have now changed so that UNDEFINED is returned on mismatch:
undefinedp(Stdio.Buffer("1 2-3")->match("%d%d%d"));
(2) Result: 0
undefinedp(Stdio.Buffer("#1 2-3")->match("%d%d%d"));
(3) Result: 1
This one is also fun:
Stdio.Buffer("1 2-3")->match("%0s%d%d%d");
(4) Result: "12-3"
pike-devel@lists.lysator.liu.se