php修改方法参数类型,自己写PHP扩展之操作类的属性和方法 | 学步园

声明:本文为斯人原创,全部为作者一一分析得之,有不对的地方望赐教。

欢迎转载,转载请注明出处 。

本文地址:http://imsiren.com/archives/581

类创建好了..

那么类肯定不止这些东西,它由继承,属性,返回值等.

1.方法的参数.

有方法,该方法就可能要有参数.参数是如何传递过来的呢?

如果看过之前的文章.那么你肯定就知道了..是的 与普通函数的参数相同.

声明char类型的指针用来保存参数的值.

声明int类型的变量来保存的参数长度

然后用到 zend_parse_parameters函数

zend_parse_parameters(``,`< char *type_spec>`,`< ...>`)

该参数有几个重要的参数

第一个是参数的个数

第二个比较重要,它指定接收参数的类型

下面这份清单完整地列举出了我们可以指定接收的参数类型:

l – 长整数

d – 双精度浮点数

s – 字符串 (也可能是空字节)和其长度

b – 布尔值

r – 资源, 保存在 zval*

a – 数组, 保存在 zval*

o – (任何类的)对象, 保存在 zval*

O – (由class entry 指定的类的)对象, 保存在 zval*

z – 实际的 zval*

下面的一些字符在类型说明字符串(就是那个 char *type_spec)中具有特别的含义:

| – 表明剩下的参数都是可选参数。如果用户没有传进来这些参数值,那么这些值就会被初始化成默认值。

/ – 表明参数解析函数将会对剩下的参数以 SEPARATE_ZVAL_IF_NOT_REF() 的方式来提供这个参数的一份拷贝,除非这些参数是一个引用。

! – 表明剩下的参数允许被设定为 NULL(仅用在 a、o、O、r和z身上)。如果用户传进来了一个 NULL 值,则存储该参数的变量将会设置为 NULL。

函数 get接收两个参数 ,第一个参数是必填字符串类型,第二个参数是可选为整型.

PHP代码如下

function get($name,$age=0){

}

如果要在扩展里实现这样的功能,zend_parse_parameters的使用如下

char* name;

int name_length;

int age;

int age_length;

zend_parse_parameters(ZEND_NUM_ARGS ,”s|l”,&name,&name_length,&age,&age_len)

zend_parse_parameters 执行失败的话会返回FAILURE.

执行成功后,name就是第一个参数的值,age就是第二个参数的值

我们甚至可以调用php_printf函数来输出.

2.类的属性

这类的内容在上一篇文章中其实已经讲清楚了.

用zend_declare_property_*一系列函数来创建我们的属性.当然是在PHP_MINIT_FUNCTION函数中创建

以 zend_declare_property_null为例:

zend_declare_property_null(``,`< char *name>`,`< int name_length>`,`< int access_type TSRMLS_DC>`)

ce :是一个zend_class_entry的指针.

name :是属性的名称

length :属性名称的长度

access_type:属性的访问级别.

还有其他几个函数 用法一样.

zend_declare_property_bool

zend_declare_property_double

zend_declare_property_ex

zend_declare_property_long

zend_declare_property_null

zend_declare_property_string

zend_declare_property_stringl

3.读取属性

创建了属性,那么该如何读取此属性呢?

zend_read_property(``,`< zval *object>`,`< char *name>`,`< int name_length>`,`< zend_bool silent TSRMLS_DC>`);

就要使用这个函数了,它将获取到的属性信息返回到一个zval结构体中

这时候要用到函数getThis();

这个函数会返回一个zval的指针.

因为是一个对象 所以保存在结构体_zend_object_value 中

typedef struct _zend_object_value {

zend_object_handle handle;

zend_object_handlers *handlers;

} zend_object_value;

第一个参数会调用 zend_object_handler所指向的函数指针get_class_entry来获取当前执行的类的信息.

第一个参数应该是 Z_OBJEC_P(getThis());

第二个参数是 getThis();

第三个参数是要获取的属性

第四个参数是属性的长度.

修改之后的getproperty方法

PHP_METHOD(Person,getproperty){

zval* self=getThis();

zval* name;

name=zend_read_property(Z_OBJCE_P(self),self,ZEND_STRL("name"),0 TSRMLS_CC);

php_printf("%s",name->value.str.val);

}

4.设置属性

该如何更新属性的值呢?

同样给我们提供了一个函数

zend_update_property(``,`< zval *object>`,`< char *name>`,`< int name_length>`,`< zval *value TSRMLS_DC>`)

前四个参数与zend_read_property相同.

不同的是最后一个zval*value.它是我们属性的值..因为他是一个zval的指针,所以我们需要将通过zend_parse_parameters获取到的参数转为一个zval的指针.

修改后的setproperty方法.

PHP_METHOD(Person,setproperty){

char *key=NULL;

int key_len;

char *val=NULL;

int val_len;

zval* self=getThis();

zval* value;

if(zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC,"ss",&key,&key_len,&val,&val_len)==FAILURE){

return;

}

MAKE_STD_ZVAL(value);

ZVAL_STRINGL(value,val,val_len,1);

zend_update_property(Z_OBJCE_P(self),self,key,key_len,value TSRMLS_CC);

最后make && make install,重启apache.

这样我们在 php代码里.<?php

$a=new Person();

$a->setproperty("name","this is siren");

$a->getproperty();

?>

就可以输出我们通过setproperty设置的值了.

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值