Revision | d84bc02475e8b8e4adc094e41acd8a1e54d0e8ce (tree) |
---|---|
Zeit | 2011-01-25 00:21:29 |
Autor | pukiwikiadmin <pukiwikiadmin> |
Commiter | pukiwikiadmin |
This commit was manufactured by cvs2svn to create branch 'branch_r1_4_7'.
@@ -0,0 +1,316 @@ | ||
1 | +<?php | |
2 | +// $Id: spam_util.php,v 1.1 2011-01-24 15:19:36 henoheno Exp $ | |
3 | +// Copyright (C) 2006-2009, 2011 PukiWiki Developers Team | |
4 | +// License: GPL v2 or (at your option) any later version | |
5 | +// | |
6 | +// Functions for Concept-work of spam-uri metrics | |
7 | + | |
8 | + | |
9 | +// --------------------- | |
10 | +// Compat etc | |
11 | + | |
12 | +// (PHP 4 >= 4.2.0): var_export(): mail-reporting and dump related | |
13 | +if (! function_exists('var_export')) { | |
14 | + function var_export() { | |
15 | + return 'var_export() is not found on this server' . "\n"; | |
16 | + } | |
17 | +} | |
18 | + | |
19 | +// (PHP 4 >= 4.2.0): preg_grep() enables invert option | |
20 | +function preg_grep_invert($pattern = '//', $input = array()) | |
21 | +{ | |
22 | + static $invert; | |
23 | + if (! isset($invert)) $invert = defined('PREG_GREP_INVERT'); | |
24 | + | |
25 | + if ($invert) { | |
26 | + return preg_grep($pattern, $input, PREG_GREP_INVERT); | |
27 | + } else { | |
28 | + $result = preg_grep($pattern, $input); | |
29 | + if ($result) { | |
30 | + return array_diff($input, preg_grep($pattern, $input)); | |
31 | + } else { | |
32 | + return $input; | |
33 | + } | |
34 | + } | |
35 | +} | |
36 | + | |
37 | + | |
38 | +// --------------------- | |
39 | +// Utilities | |
40 | + | |
41 | + | |
42 | +if (! function_exists('htmlsc')) { | |
43 | + // Interface with PukiWiki | |
44 | + if (! defined('CONTENT_CHARSET')) define('CONTENT_CHARSET', 'ISO-8859-1'); | |
45 | + | |
46 | + // Sugar with default settings | |
47 | + function htmlsc($string = '', $flags = ENT_QUOTES, $charset = CONTENT_CHARSET) | |
48 | + { | |
49 | + return htmlspecialchars($string, $flags, $charset); // htmlsc() | |
50 | + } | |
51 | +} | |
52 | + | |
53 | +// Very roughly, shrink the lines of var_export() | |
54 | +// NOTE: If the same data exists, it must be corrupted. | |
55 | +function var_export_shrink($expression, $return = FALSE, $ignore_numeric_keys = FALSE) | |
56 | +{ | |
57 | + $result = var_export($expression, TRUE); | |
58 | + | |
59 | + $result = preg_replace( | |
60 | + // Remove a newline and spaces | |
61 | + '# => \n *array \(#', ' => array (', | |
62 | + $result | |
63 | + ); | |
64 | + | |
65 | + if ($ignore_numeric_keys) { | |
66 | + $result =preg_replace( | |
67 | + // Remove numeric keys | |
68 | + '#^( *)[0-9]+ => #m', '$1', | |
69 | + $result | |
70 | + ); | |
71 | + } | |
72 | + | |
73 | + if ($return) { | |
74 | + return $result; | |
75 | + } else { | |
76 | + echo $result; | |
77 | + return NULL; | |
78 | + } | |
79 | +} | |
80 | + | |
81 | +// Data structure: Create an array they _refer_only_one_ value | |
82 | +function one_value_array($num = 0, $value = NULL) | |
83 | +{ | |
84 | + $num = max(0, intval($num)); | |
85 | + $array = array(); | |
86 | + | |
87 | + for ($i = 0; $i < $num; $i++) { | |
88 | + $array[] = & $value; | |
89 | + } | |
90 | + | |
91 | + return $array; | |
92 | +} | |
93 | + | |
94 | +// Reverse $string with specified delimiter | |
95 | +function delimiter_reverse($string = 'foo.bar.example.com', $from_delim = '.', $to_delim = NULL) | |
96 | +{ | |
97 | + $to_null = ($to_delim === NULL); | |
98 | + | |
99 | + if (! is_string($from_delim) || (! $to_null && ! is_string($to_delim))) { | |
100 | + return FALSE; | |
101 | + } | |
102 | + if (is_array($string)) { | |
103 | + // Map, Recurse | |
104 | + $count = count($string); | |
105 | + $from = one_value_array($count, $from_delim); | |
106 | + if ($to_null) { | |
107 | + // Note: array_map() vanishes all keys | |
108 | + return array_map('delimiter_reverse', $string, $from); | |
109 | + } else { | |
110 | + $to = one_value_array($count, $to_delim); | |
111 | + // Note: array_map() vanishes all keys | |
112 | + return array_map('delimiter_reverse', $string, $from, $to); | |
113 | + } | |
114 | + } | |
115 | + if (! is_string($string)) { | |
116 | + return FALSE; | |
117 | + } | |
118 | + | |
119 | + // Returns com.example.bar.foo | |
120 | + if ($to_null) $to_delim = & $from_delim; | |
121 | + return implode($to_delim, array_reverse(explode($from_delim, $string))); | |
122 | +} | |
123 | + | |
124 | +// ksort() by domain | |
125 | +function ksort_by_domain(& $array) | |
126 | +{ | |
127 | + $sort = array(); | |
128 | + foreach(array_keys($array) as $key) { | |
129 | + $reversed = delimiter_reverse($key); | |
130 | + if ($reversed !== FALSE) { | |
131 | + $sort[$reversed] = $key; | |
132 | + } | |
133 | + } | |
134 | + ksort($sort, SORT_STRING); | |
135 | + | |
136 | + $result = array(); | |
137 | + foreach($sort as $key) { | |
138 | + $result[$key] = & $array[$key]; | |
139 | + } | |
140 | + | |
141 | + $array = $result; | |
142 | +} | |
143 | + | |
144 | +// Roughly strings(1) using PCRE | |
145 | +// This function is useful to: | |
146 | +// * Reduce the size of data, from removing unprintable binary data | |
147 | +// * Detect _bare_strings_ from binary data | |
148 | +// References: | |
149 | +// http://www.freebsd.org/cgi/man.cgi?query=strings (Man-page of GNU strings) | |
150 | +// http://www.pcre.org/pcre.txt | |
151 | +// Note: mb_ereg_replace() is one of mbstring extension's functions | |
152 | +// and need to init its encoding. | |
153 | +function strings($binary = '', $min_len = 4, $ignore_space = FALSE, $multibyte = FALSE) | |
154 | +{ | |
155 | + // String only | |
156 | + $binary = (is_array($binary) || $binary === TRUE) ? '' : strval($binary); | |
157 | + | |
158 | + $regex = $ignore_space ? | |
159 | + '[^[:graph:] \t\n]+' : // Remove "\0" etc, and readable spaces | |
160 | + '[^[:graph:][:space:]]+'; // Preserve readable spaces if possible | |
161 | + | |
162 | + $binary = $multibyte ? | |
163 | + mb_ereg_replace($regex, "\n", $binary) : | |
164 | + preg_replace('/' . $regex . '/s', "\n", $binary); | |
165 | + | |
166 | + if ($ignore_space) { | |
167 | + $binary = preg_replace( | |
168 | + array( | |
169 | + '/[ \t]{2,}/', | |
170 | + '/^[ \t]/m', | |
171 | + '/[ \t]$/m', | |
172 | + ), | |
173 | + array( | |
174 | + ' ', | |
175 | + '', | |
176 | + '' | |
177 | + ), | |
178 | + $binary); | |
179 | + } | |
180 | + | |
181 | + if ($min_len > 1) { | |
182 | + // The last character seems "\n" or not | |
183 | + $br = (! empty($binary) && $binary[strlen($binary) - 1] == "\n") ? "\n" : ''; | |
184 | + | |
185 | + $min_len = min(1024, intval($min_len)); | |
186 | + $regex = '/^.{' . $min_len . ',}/S'; | |
187 | + $binary = implode("\n", preg_grep($regex, explode("\n", $binary))) . $br; | |
188 | + } | |
189 | + | |
190 | + return $binary; | |
191 | +} | |
192 | + | |
193 | + | |
194 | +// --------------------- | |
195 | +// Utilities: Arrays | |
196 | + | |
197 | +// Count leaves (A leaf = value that is not an array, or an empty array) | |
198 | +function array_count_leaves($array = array(), $count_empty = FALSE) | |
199 | +{ | |
200 | + if (! is_array($array) || (empty($array) && $count_empty)) return 1; | |
201 | + | |
202 | + // Recurse | |
203 | + $count = 0; | |
204 | + foreach ($array as $part) { | |
205 | + $count += array_count_leaves($part, $count_empty); | |
206 | + } | |
207 | + return $count; | |
208 | +} | |
209 | + | |
210 | +// Merge two leaves | |
211 | +// Similar to PHP array_merge_leaves(), except strictly preserving keys as string | |
212 | +function array_merge_leaves($array1, $array2, $sort_keys = TRUE) | |
213 | +{ | |
214 | + // Array(s) only | |
215 | + $is_array1 = is_array($array1); | |
216 | + $is_array2 = is_array($array2); | |
217 | + if ($is_array1) { | |
218 | + if ($is_array2) { | |
219 | + ; // Pass | |
220 | + } else { | |
221 | + return $array1; | |
222 | + } | |
223 | + } else if ($is_array2) { | |
224 | + return $array2; | |
225 | + } else { | |
226 | + return $array2; // Not array ($array1 is overwritten) | |
227 | + } | |
228 | + | |
229 | + $keys_all = array_merge(array_keys($array1), array_keys($array2)); | |
230 | + if ($sort_keys) sort($keys_all, SORT_STRING); | |
231 | + | |
232 | + $result = array(); | |
233 | + foreach($keys_all as $key) { | |
234 | + $isset1 = isset($array1[$key]); | |
235 | + $isset2 = isset($array2[$key]); | |
236 | + if ($isset1 && $isset2) { | |
237 | + // Recurse | |
238 | + $result[$key] = array_merge_leaves($array1[$key], $array2[$key], $sort_keys); | |
239 | + } else if ($isset1) { | |
240 | + $result[$key] = & $array1[$key]; | |
241 | + } else { | |
242 | + $result[$key] = & $array2[$key]; | |
243 | + } | |
244 | + } | |
245 | + return $result; | |
246 | +} | |
247 | + | |
248 | +// An array-leaves to a flat array | |
249 | +function array_flat_leaves($array, $unique = TRUE) | |
250 | +{ | |
251 | + if (! is_array($array)) return $array; | |
252 | + | |
253 | + $tmp = array(); | |
254 | + foreach(array_keys($array) as $key) { | |
255 | + if (is_array($array[$key])) { | |
256 | + // Recurse | |
257 | + foreach(array_flat_leaves($array[$key]) as $_value) { | |
258 | + $tmp[] = $_value; | |
259 | + } | |
260 | + } else { | |
261 | + $tmp[] = & $array[$key]; | |
262 | + } | |
263 | + } | |
264 | + | |
265 | + return $unique ? array_values(array_unique($tmp)) : $tmp; | |
266 | +} | |
267 | + | |
268 | +// $array['something'] => $array['wanted'] | |
269 | +function array_rename_keys(& $array, $keys = array('from' => 'to'), $force = FALSE, $default = '') | |
270 | +{ | |
271 | + if (! is_array($array) || ! is_array($keys)) return FALSE; | |
272 | + | |
273 | + // Nondestructive test | |
274 | + if (! $force) { | |
275 | + foreach(array_keys($keys) as $from) { | |
276 | + if (! isset($array[$from])) { | |
277 | + return FALSE; | |
278 | + } | |
279 | + } | |
280 | + } | |
281 | + | |
282 | + foreach($keys as $from => $to) { | |
283 | + if ($from === $to) continue; | |
284 | + if (! $force || isset($array[$from])) { | |
285 | + $array[$to] = & $array[$from]; | |
286 | + unset($array[$from]); | |
287 | + } else { | |
288 | + $array[$to] = $default; | |
289 | + } | |
290 | + } | |
291 | + | |
292 | + return TRUE; | |
293 | +} | |
294 | + | |
295 | +// Remove redundant values from array() | |
296 | +function array_unique_recursive($array = array()) | |
297 | +{ | |
298 | + if (! is_array($array)) return $array; | |
299 | + | |
300 | + $tmp = array(); | |
301 | + foreach($array as $key => $value){ | |
302 | + if (is_array($value)) { | |
303 | + $array[$key] = array_unique_recursive($value); | |
304 | + } else { | |
305 | + if (isset($tmp[$value])) { | |
306 | + unset($array[$key]); | |
307 | + } else { | |
308 | + $tmp[$value] = TRUE; | |
309 | + } | |
310 | + } | |
311 | + } | |
312 | + | |
313 | + return $array; | |
314 | +} | |
315 | + | |
316 | +?> |