From 1d2dc36ac1baca6ff63f2a082cc7d4c6439fc1de Mon Sep 17 00:00:00 2001 From: Tim Starling Date: Tue, 21 Nov 2006 10:38:07 +0000 Subject: [PATCH] Collection of generic string functions and classes --- includes/StringUtils.php | 263 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 263 insertions(+) create mode 100644 includes/StringUtils.php diff --git a/includes/StringUtils.php b/includes/StringUtils.php new file mode 100644 index 0000000000..8a0e478c81 --- /dev/null +++ b/includes/StringUtils.php @@ -0,0 +1,263 @@ +cb(), $subject, $flags ); + } + + /** + * More or less "markup-safe" explode() + * Ignores any instances of the separator inside <...> + * @param string $separator + * @param string $text + * @return array + */ + static function explodeMarkup( $separator, $text ) { + $placeholder = "\x00"; + + // Remove placeholder instances + $text = str_replace( $placeholder, '', $text ); + + // Replace instances of the separator inside HTML-like tags with the placeholder + $replacer = new DoubleReplacer( $separator, $placeholder ); + $cleaned = StringUtils::delimiterReplaceCallback( '<', '>', $replacer->cb(), $text ); + + // Explode, then put the replaced separators back in + $items = explode( $separator, $cleaned ); + foreach( $items as $i => $str ) { + $items[$i] = str_replace( $placeholder, $separator, $str ); + } + + return $items; + } + + /** + * Escape a string to make it suitable for inclusion in a preg_replace() + * replacement parameter. + * + * @param string $string + * @return string + */ + static function escapeRegexReplacement( $string ) { + $string = str_replace( '\\', '\\\\', $string ); + $string = str_replace( '$', '\\$', $string ); + return $string; + } +} + +/** + * Base class for "replacers", objects used in preg_replace_callback() and + * StringUtils::delimiterReplaceCallback() + */ +class Replacer { + function cb() { + return array( &$this, 'replace' ); + } +} + +/** + * Class to replace regex matches with a string similar to that used in preg_replace() + */ +class RegexlikeReplacer extends Replacer { + var $r; + function __construct( $r ) { + $this->r = $r; + } + + function replace( $matches ) { + $pairs = array(); + foreach ( $matches as $i => $match ) { + $pairs["\$$i"] = $match; + } + return strtr( $this->r, $pairs ); + } + +} + +/** + * Class to perform secondary replacement within each replacement string + */ +class DoubleReplacer extends Replacer { + function __construct( $from, $to, $index = 0 ) { + $this->from = $from; + $this->to = $to; + $this->index = $index; + } + + function replace( $matches ) { + return str_replace( $this->from, $this->to, $matches[$this->index] ); + } +} + +/** + * Class to perform replacement based on a simple hashtable lookup + */ +class HashtableReplacer extends Replacer { + var $table, $index; + + function __construct( $table, $index = 0 ) { + $this->table = $table; + $this->index = $index; + } + + function replace( $matches ) { + return $this->table[$matches[$this->index]]; + } +} + +/** + * Replacement array for FSS with fallback to strtr() + * Supports lazy initialisation of FSS resource + */ +class ReplacementArray { + /*mostly private*/ var $data = false; + /*mostly private*/ var $fss = false; + + /** + * Create an object with the specified replacement array + * The array should have the same form as the replacement array for strtr() + */ + function __construct( $data = array() ) { + $this->data = $data; + } + + function __sleep() { + return array( 'data' ); + } + + function __wakeup() { + $this->fss = false; + } + + /** + * Set the whole replacement array at once + */ + function setArray( $data ) { + $this->data = $data; + $this->fss = false; + } + + function getArray() { + return $this->data; + } + + /** + * Set an element of the replacement array + */ + function setPair( $from, $to ) { + $this->data[$from] = $to; + $this->fss = false; + } + + function mergeArray( $data ) { + $this->data = array_merge( $this->data, $data ); + $this->fss = false; + } + + function merge( $other ) { + $this->data = array_merge( $this->data, $other->data ); + $this->fss = false; + } + + function replace( $subject ) { + if ( function_exists( 'fss_prep_replace' ) ) { + if ( $this->fss === false ) { + $this->fss = fss_prep_replace( $this->data ); + } + return fss_exec_replace( $this->fss, $subject ); + } else { + return strtr( $subject, $this->data ); + } + } +} + +?> -- 2.20.1