2

I am looking for ways to match a range of characters and assumed the following regEx would only match characters in the range of hex codes between 20 and 7E. However, it also matches chr(10) (line feed), in fact, the following prints "passed":

echo preg_match("/^[\x20-\x7E]*$/", chr(10)) ? 'passed' : 'failed';

Any idea why and how to match that range?

Dmitri Zaitsev
  • 13,548
  • 11
  • 76
  • 110

1 Answers1

2

chr(10) is end of line, so you should add modifier D.

If this modifier is set, a dollar metacharacter in the pattern matches only at the end of the subject string. Without this modifier, a dollar also matches immediately before the final character if it is a newline (but not before any other newlines).

//                               v
echo preg_match("/^[\x20-\x7E]*$/D", chr(10)) ? 'passed' : 'failed';
//                               ^
sectus
  • 15,605
  • 5
  • 55
  • 97
  • 2
    ...or use `\A` and `\z` instead of `^` and `$` to force anchoring at the very start and end of the string. – Tim Pietzcker Sep 03 '13 at 07:51
  • @TimPietzcker Nevertheless, isn't M42 correct that the star is optional and the regex will pass not just for form feeds but like `chr(14)` even if you have used `\A` or `\z`? – Ibrahim Najjar Sep 03 '13 at 07:57
  • 1
    @TimPietzcker, you are right. It's better to use \A and \z cause pattern would be independent from PHP. – sectus Sep 03 '13 at 07:59
  • @Sniffer: No. The anchors are there to ensure that the entire string matches, and `chr(14)` is definitely outside of the range defined by the character class. The problem is that `chr(10)` is treated specially by `$`, as sectus correctly states. – Tim Pietzcker Sep 03 '13 at 07:59
  • @Sniffer, This is the [Escape sequence](http://www.php.net/manual/en/regexp.reference.escape.php). – sectus Sep 03 '13 at 08:01
  • @TimPietzcker I see I see I see, I don't know how I missed that. It happens sometimes. Anyway everything is OK now. Thanks to both of you. – Ibrahim Najjar Sep 03 '13 at 08:07
  • Many thanks, both solutions by @sectus and @TimPietzcker work great! I see now that the new line `chr(10)` is treated specially by `$`, which I still find counter-intuitive, there are sadly no examples in the [manual](http://www.php.net/manual/en/regexp.reference.anchors.php) – Dmitri Zaitsev Sep 03 '13 at 08:20
  • 1
    @DmitriZaitsev: Read about [anchors](http://www.regular-expressions.info/anchors.html) here, especially the section "String ending with a Line Break". – Tim Pietzcker Sep 03 '13 at 10:00
  • @TimPietzcker Thanks, fantastic tutorial! The best I've seen! So none of the two solution works in JavaScript! Arrgh! Have to use /m option instead. – Dmitri Zaitsev Sep 03 '13 at 12:18