php扩展开发之传参
最近跟着服务器组同学学写C++,不是想转做C++开发,只是想借此机会锻炼一下自己.php的扩展不止可以使用原生的C,同样的可以使用C++来开发扩展来扩展我们的php.不过今天我们还不会谈C++扩展php,依旧还是原生的C来扩展我们的php.上一篇,我给了一个简单的扩展开发HelloWorld的例子.除了证明我们可以用C扩展php,它对我们日常工作可能要解决的问题来说毫无作用.今天我们来看一下php扩展传参是如果实现的,我们在日常的php开发当中写函数时要传参,同样我们看系统提供的函数中也有参数,但是我们在扩展函数的声明中是没有传参相关的参数的,那么它是如何实现的哪?
Zend API提供了解析参数的函数帮我们来解决这个问题:
ZEND_API int zend_parse_parameters(int num_args TSRMLS_DC, const char *type_spec, …)
ZEND_API int zend_get_parameters(int ht, int param_count, …)
我这里列了2个函数,zend_parse_parameters和zend_get_parameters,你可以在Zend/zend_API.c中找到他们.今天我们主要了解的是zend_parse_parameters,应为这是现阶段php5扩展中开发主要的解析参数的函数,而zend_get_parameters是针对php5之前的扩展用到的.需要你需要扩展老版本的php或者兼容旧的版本,请自行google翻阅资料,我个人觉得其意义不是很大,这里就不再多加探讨了.
zend_parse_parameters有2个主要参数,还有若干可变的参数,可变参数的作用就是接受我们php脚本中传递给扩展的参数.我们先看看这2个主要参数的作用吧:
int num_args就是本函数参数的个数,const char *type_spec是一个用于格式化的字符串,类似C里面的printf,不过他们2个却是完全不一样的.
参数 代表着的类型
b Boolean
l Integer 整型
d Floating point 浮点型
s String 字符串
r Resource 资源
a Array 数组
o Object instance 对象
O Object instance of a specified type 特定类型的对象
z Non-specific zval 任意类型~
Z zval**类型
f 表示函数、方法名称,PHP5.1里貌似木有... ...
参数 对应C里的数据类型
b zend_bool
l
long
d
double
s
char
*,
int
前者接收指针,后者接收长度
r zval*
a zval*
o zval*
O zval*, zend_class_entry*
z zval*
Z zval**
<?php $x = 1; $y = 2; exchange_num($x,$y); echo $x."\n".$y."\n"; function exchange_num(&$a,&$b){ $c = $a; $a = $b; $b = $c; } //2 //1
PHP_FUNCTION(king_exchange_number){ long num1,num2; zval *arg1,*arg2; if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC,"zz", &arg1, &arg2) == FAILURE){ RETURN_NULL(); } num1 = Z_LVAL_P(arg1); num2 = Z_LVAL_P(arg2); php_printf("num1:%ld,num2:%ld\n",num1,num2); ZVAL_LONG(arg1,num2); ZVAL_LONG(arg2,num1); RETURN_NULL(); }
PHP_FE(king_exchange_number,NULL)
<?php $num1 = 11; $num2 = 89; king_exchange_number($num1,$num2); echo "\$num1:$num1\n"; echo "\$num2:$num2\n"; //$num1:89 //$num2:11
近期评论