I've added an extra option extract() to have potential variable names passed
to a user defined callback function. If this function then returns true,
it's extracted, if not it's not.
Anyone care to apply/check it?
Eg.:
<?php
function extract_callback($varname){
return preg_match('/^var/', $varname);
}
$var['var_1'] = 1;
$var['var_2'] = 1;
$var['blaat'] = 1;
extract($var, EXTR_USER_CALLBACK, 'extract_callback');
printf('var_1: %s <br>', $var_1);
printf('var_2: %s <br>', $var_2);
printf('blaat: %s <br>', $blaat);
?>
Index: array.c
===================================================================
RCS file: /repository/php4/ext/standard/array.c,v
retrieving revision 1.156
diff -u -u -r1.156 array.c
--- array.c 5 Feb 2002 20:43:48 -0000 1.156
+++ array.c 25 Feb 2002 16:07:10 -0000
@@ -59,7 +59,8 @@
#define EXTR_PREFIX_INVALID 4
#define EXTR_PREFIX_IF_EXISTS 5
#define EXTR_IF_EXISTS 6
-
+#define EXTR_USER_CALLBACK 7
+
#define SORT_REGULAR 0
#define SORT_NUMERIC 1
#define SORT_STRING 2
@@ -86,7 +87,8 @@
REGISTER_LONG_CONSTANT("EXTR_PREFIX_INVALID", EXTR_PREFIX_INVALID, CONST_CS |
CONST_PERSISTENT);
REGISTER_LONG_CONSTANT("EXTR_PREFIX_IF_EXISTS", EXTR_PREFIX_IF_EXISTS,
CONST_CS | CONST_PERSISTENT);
REGISTER_LONG_CONSTANT("EXTR_IF_EXISTS", EXTR_IF_EXISTS, CONST_CS |
CONST_PERSISTENT);
-
+ REGISTER_LONG_CONSTANT("EXTR_USER_CALLBACK", EXTR_USER_CALLBACK, CONST_CS |
+CONST_PERSISTENT);
+
REGISTER_LONG_CONSTANT("SORT_ASC", SORT_ASC, CONST_CS | CONST_PERSISTENT);
REGISTER_LONG_CONSTANT("SORT_DESC", SORT_DESC, CONST_CS | CONST_PERSISTENT);
@@ -1137,7 +1139,7 @@
PHP_FUNCTION(extract)
{
zval **var_array, **z_extract_type, **prefix;
- zval **entry, *data;
+ zval **entry, *data, *user_callback_retval, **user_callback_args[1],
+*user_callback_arg;
char *var_name;
smart_str final_name = {0};
ulong num_key;
@@ -1163,6 +1165,11 @@
php_error(E_WARNING, "%s() expects a prefix to be
specified",
get_active_function_name(TSRMLS_C));
return;
+
+ }else if(extract_type == EXTR_USER_CALLBACK){
+ php_error(E_WARNING, "%s() expects a user defined
+function to be specified",
+ get_active_function_name(TSRMLS_C));
+ return;
}
break;
@@ -1180,7 +1187,7 @@
break;
}
- if (extract_type < EXTR_OVERWRITE || extract_type > EXTR_IF_EXISTS) {
+ if (extract_type < EXTR_OVERWRITE || extract_type > EXTR_USER_CALLBACK) {
php_error(E_WARNING, "Unknown extract type in call to %s()",
get_active_function_name(TSRMLS_C));
return;
@@ -1248,8 +1255,30 @@
} else
smart_str_appendl(&final_name,
var_name, var_name_len);
}
- break;
-
+ break;
+
+ case EXTR_USER_CALLBACK:
+ user_callback_arg = emalloc(sizeof(zval));
+ MAKE_STD_ZVAL(user_callback_arg);
+ ZVAL_STRING(user_callback_arg, var_name, 0);
+
+ *(user_callback_args[0]) = user_callback_arg;
+
+ if(call_user_function_ex(EG(function_table), NULL,
+*prefix, &user_callback_retval, 1, user_callback_args, 0, NULL TSRMLS_CC) != SUCCESS){
+ php_error(E_WARNING, "Failed to call user
+function: %s()", Z_STRVAL_PP(prefix));
+ return;
+ }
+ efree(user_callback_arg);
+
+ if(!Z_BVAL_P(user_callback_retval)){
+
+zend_hash_move_forward_ex(Z_ARRVAL_PP(var_array), &pos);
+ continue;
+ }else{
+ smart_str_appendl(&final_name, var_name,
+var_name_len);
+ }
+
+ break;
+
default:
if (!var_exists)
smart_str_appendl(&final_name, var_name,
var_name_len);
--
PHP Development Mailing List <http://www.php.net/>
To unsubscribe, visit: http://www.php.net/unsub.php