用C实现PHP扩展类的步骤_PHP教程
前面简单介绍了用C语言实现PHP扩展的步骤,见用C开发PHP扩展的步骤,那个是扩展一个函数,这里讲述一下如何用C扩展类。
准备实现的类如下:
[php]
class Rectangle{
private $_width;
private $_height;
public function __construct($width, $height){
$this->_width = $width;
$this->_height = $height;
}
public function clone(){
return new Rectangle($this->_width, $this->_height);
}
public function setWidth($width){
$this->_width = $width;
}
public function setHeight($height){
$this->_height = $height;
}
public function getWidth(){
return $this->_width;
}
public function getHeight(){
return $this->_height;
}
public function getArea(){
return $this->_width * $this->_height;
}
public function getCircle(){
return ($this->_width + $this->_height) * 2;
}
}
实现类扩展的步骤如下:(首先下载PHP源码,这里使用的是php-5.2.8)
1,建立扩展骨架
[php]
cd php-5.2.8/ext
./ext_skel --extname=class_ext
2,修改编译参数
[php]
cd php-5.2.8/ext/class_ext
vi config.m4
去掉PHP_ARG_ENABLE(class_ext, whether to enable class_ext support,和
[ --enable-class_ext Enable class_ext support])两行前面的dnl,修改后为:
[php]
dnl Otherwise use enable:
PHP_ARG_ENABLE(class_ext, whether to enable class_ext support,
dnl Make sure that the comment is aligned:
[ --enable-class_ext Enable class_ext support])
3,编写C代码
[php]
cd php-5.2.8/ext/class_ext
vi php_class_ext.h
#在 PHP_FUNCTION(confirm_class_ext_compiled); 后面增加申明函数;
[php]
PHP_METHOD(Rectangle,__construct);
PHP_METHOD(Rectangle,clone);
PHP_METHOD(Rectangle,setWidth);
PHP_METHOD(Rectangle,setHeight);
PHP_METHOD(Rectangle,getWidth);
PHP_METHOD(Rectangle,getHeight);
PHP_METHOD(Rectangle,getArea);
PHP_METHDO(Rectangle,getCircle);
[php]
vi class_ext.c
#申明方法的参数,注册到函数表中
[php]
ZEND_BEGIN_ARG_INFO(arg_construct,2)
ZEND_ARG_INFO(0, width)
ZEND_ARG_INFO(0, height)
ZEND_END_ARG_INFO()
ZEND_BEGIN_ARG_INFO(arg_set_width,1)
ZEND_ARG_INFO(0, width)
ZEND_END_ARG_INFO()
ZEND_BEGIN_ARG_INFO(arg_set_height,1)
ZEND_ARG_INFO(0, height)
ZEND_END_ARG_INFO()
const zend_function_entry class_ext_functions[] = {
PHP_FE(confirm_class_ext_compiled, NULL)
PHP_ME(Rectangle, __construct, arg_construct, ZEND_ACC_CTOR|ZEND_ACC_PUBLIC)
PHP_ME(Rectangle, clone, NULL, ZEND_ACC_PUBLIC)
PHP_ME(Rectangle, setWidth, NULL, ZEND_ACC_PUBLIC)
PHP_ME(Rectangle, setHeight, NULL, ZEND_ACC_PUBLIC)
PHP_ME(Rectangle, getWidth, NULL, ZEND_ACC_PUBLIC)
PHP_ME(Rectangle, getHeight, NULL, ZEND_ACC_PUBLIC)
PHP_ME(Rectangle, getArea, NULL, ZEND_ACC_PUBLIC)
PHP_ME(Rectangle, getCircle, NULL, ZEND_ACC_PUBLIC)
{NULL, NULL, NULL} /* Must be the last line in class_ext_functions[] */
};
[php]
#其中ZEND_ACC_CTOR表示构造函数,ZEND_ACC_PUBLIC表示访问权限为PUBLIC。
[php]
#接下来,在模块初始化函数中注册并初始化类
[php]
zend_class_entry *Rectangle_ce; //zend内部类结构变量
PHP_MINIT_FUNCTION(class_ext)
{
zend_class_entry Rectangle;
INIT_CLASS_ENTRY(Rectanble, "Rectangle", class_ext_functions); //第二个参数为类名,第三个参数为类的函数列表
Rectangle_ce = zend_register_internal_class_ex(&Rectangle, NULL, NULL TSRMLS_CC); //注册类
zend_declare_property_null(Rectangle_ce, ZEND_STRL("_width"), ZEND_ACC_PRIVATE TSRMLS_CC); //初始化类的属性_width
zend_declare_property_null(Rectangle_ce, ZEND_STRL("_height"), ZEND_ACC_PRIVATE TSRMLS_CC); //初始化类的属性_height
return SUCCESS;
}
[php]
#在文件最后增加类的成员函数的具体实现代码
[php]
PHP_METHOD(Rectangle, __construct)
{
long width,height;
if(zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "ll", &width, &height) == FAILURE){ //获取构造函数的两个函数参数_width和_height
WRONG_PARAM_COUNT;
}
if( width
width = 1; //如果_width为0,则赋默认值1
}
if( height
height = 1; //如果_height为0,则赋默认值1
}
zend_update_property_long(Z_OBJCE_P(getThis()), getThis(), ZEND_STRL("_width"), width TSRMLS_CC); //更新类成员变量_width的值
zend_update_property_long(Z_OBJCE_P(getThis()), getThis(), ZEND_STRL("_height"), height TSRMLS_CC); //更新类成员变量_height的值
RETURN_TRUE;
}
PHP_METHOD(Rectangle, clone)
{
zval *clone_obj;
zval *width,*height;
MAKE_STD_ZVAL(clone_obj);
object_init_ex(clone_obj, Rectangle_ce); //初始化对象,对象所属的类为Rectangle_ce
width = zend_read_property(Z_OBJCE_P(getThis()), getThis(), ZEND_STRL("_width"), 0 TSRMLS_CC); //获取类成员变量_width的值
height = zend_read_property(Z_OBJCE_P(getThis()), getThis(), ZEND_STRL("_height"), 0 TSRMLS_CC); //获取类成员变量_height的值
zend_update_property_long(Z_OBJCE_P(getThis()), getThis(), ZEND_STRL("_width"), width TSRMLS_CC); //更新Rectangle_ce类对象clone_obj的属性值_width
zend_update_property_long(Z_OBJCE_P(getThis()), getThis(), ZEND_STRL("_height"), height TSRMLS_CC); //更新Rectangle_ce类对象clone_obj的属性值_height
RETURN_ZVAL(clone_obj, 1, 0); //返回该对象
}
PHP_METHOD(Rectangle, setWidth()
{
long width;
if(zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l", &width) == FAILURE){
WRONG_PARAM_COUNT;
}
if( width
width = 1;
}
zend_update_property_long(Z_OBJCE_P(getThis()), getThis(), ZEND_STRL("_width"), width TSRMLS_CC); //更新类成员变量_width的值
RETURN_TRUE;
}
PHP_METHOD(Rectangle, setHeight()
{
long height;
if(zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l", &height) == FAILURE){
WRONG_PARAM_COUNT;
}
if( height
height = 1;
}
zend_update_property_long(Z_OBJCE_P(getThis()), getThis(), ZEND_STRL("_height"), height TSRMLS_CC); //更新类成员变量_height的值
RETURN_TRUE;
}
PHP_METHOD(Rectangle, getWidth)
{
zval *zWidth;
long width;
zWidth = zend_read_property(Z_OBJCE_P(getThis()), getThis(), ZEND_STRL("_width"), 0 TSRMLS_CC); //获取类成员变量_width的值
width = Z_LVAL_P(zWidth);
RETURN_LONG(width);
}
PHP_METHOD(Rectangle, getHeight)
{
zval *zHeight;
long height;
zHeight = zend_read_property(Z_OBJCE_P(getThis()), getThis(), ZEND_STRL("_height"), 0 TSRMLS_CC);
height = Z_LVAL_P(zHeight);
RETURN_LONG(height);
}
PHP_METHOD(Rectangle, getArea)
{
zval *zWidth,*zHeight;
long width,height,area;
zWidth = zend_read_property(Z_OBJCE_P(getThis()), getThis(), ZEND_STRL("_width"), 0 TSRMLS_CC);
zHeight = zend_read_property(Z_OBJCE_P(getThis()), getThis(), ZEND_STRL("_height"), 0 TSRMLS_CC);
width = Z_LVAL_P(zWidth);
height = Z_LVAL_P(zHeight);
area = width * height;
RETURN_LONG(area);
}
PHP_METHOD(Rectangle, getCircle)
{
zval *zWidth,*zHeight;
long width,height,circle;
zWidth = zend_read_property(Z_OBJCE_P(getThis()), getThis(), ZEND_STRL("_width"), 0 TSRMLS_CC);
zHeight = zend_read_property(Z_OBJCE_P(getThis()), getThis(), ZEND_STRL("_height"), 0 TSRMLS_CC);
width = Z_LVAL_P(zWidth);
height = Z_LVAL_P(zHeight);
circle = (width + height) * 2;
RETURN_LONG(circle);
}
4,编译代码
[php]
cd php-5.2.8/ext/class_ext
/usr/local/php/bin/phpize
./configure --with-php-config=/usr/local/php/bin/php-config
make
make install
此时会在php的安装路径下产生一个so文件,比如
/usr/local/php/lib/php/extensions/no-debug-non-zts-20060613/class_ext.so
修改php.ini 添加扩展extension_dir = "/usr/local/php/lib/php/extensions/no-debug-non-zts-20060613/"
[class_ext]
extension = class_ext.so
5,测试代码
[php]
$width = -10;
$height = 12;
$rectangle = new Rectangle($width, $height);
$area = $rectangle->getArea();
var_dump($area);
$circle = $rectangle->getCircle();
var_dump($circle);
$clone = $rectangle->clone();
$_area = $clone->getArea();
var_dump($_area);
$clone->setWidth(100);
$clone->setHeight(200);
$_area = $clone->getArea();
var_dump($_area);
$width = $clone->getWidth();
var_dump($width);
$height = $clone->getHeight();
var_dump($height);
结果输出:
[php]
int(12)
int(26)
int(12)
int(20000)
int(100)
int(200)

熱AI工具

Undresser.AI Undress
人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover
用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool
免費脫衣圖片

Clothoff.io
AI脫衣器

Video Face Swap
使用我們完全免費的人工智慧換臉工具,輕鬆在任何影片中換臉!

熱門文章

熱工具

記事本++7.3.1
好用且免費的程式碼編輯器

SublimeText3漢化版
中文版,非常好用

禪工作室 13.0.1
強大的PHP整合開發環境

Dreamweaver CS6
視覺化網頁開發工具

SublimeText3 Mac版
神級程式碼編輯軟體(SublimeText3)

多次調用session_start()會導致警告信息和可能的數據覆蓋。 1)PHP會發出警告,提示session已啟動。 2)可能導致session數據意外覆蓋。 3)使用session_status()檢查session狀態,避免重複調用。

AI可以幫助優化Composer的使用,具體方法包括:1.依賴管理優化:AI分析依賴關係,建議最佳版本組合,減少衝突。 2.自動化代碼生成:AI生成符合最佳實踐的composer.json文件。 3.代碼質量提升:AI檢測潛在問題,提供優化建議,提高代碼質量。這些方法通過機器學習和自然語言處理技術實現,幫助開發者提高效率和代碼質量。

session_start()iscucialinphpformanagingusersessions.1)ItInitiateSanewsessionifnoneexists,2)resumesanexistingsessions,and3)setsasesessionCookieforContinuityActinuityAccontinuityAcconActInityAcconActInityAcconAccRequests,EnablingApplicationsApplicationsLikeUseAppericationLikeUseAthenticationalticationaltication and PersersonalizedContentent。

MySQL函數可用於數據處理和計算。 1.基本用法包括字符串處理、日期計算和數學運算。 2.高級用法涉及結合多個函數實現複雜操作。 3.性能優化需避免在WHERE子句中使用函數,並使用GROUPBY和臨時表。

HTML5帶來了五個關鍵改進:1.語義化標籤提升了代碼清晰度和SEO效果;2.多媒體支持簡化了視頻和音頻嵌入;3.表單增強簡化了驗證;4.離線與本地存儲提高了用戶體驗;5.畫布與圖形功能增強了網頁的可視化效果。

Composer是PHP的依賴管理工具,通過composer.json文件管理項目依賴。 1)解析composer.json獲取依賴信息;2)解析依賴關係形成依賴樹;3)從Packagist下載並安裝依賴到vendor目錄;4)生成composer.lock文件鎖定依賴版本,確保團隊一致性和項目可維護性。

在MySQL中配置字符集和排序規則的方法包括:1.設置服務器級別的字符集和排序規則:SETNAMES'utf8';SETCHARACTERSETutf8;SETCOLLATION_CONNECTION='utf8_general_ci';2.創建使用特定字符集和排序規則的數據庫:CREATEDATABASEexample_dbCHARACTERSETutf8COLLATEutf8_general_ci;3.創建表時指定字符集和排序規則:CREATETABLEexample_table(idINT

typetraits在C 中用於編譯時類型檢查和操作,提升代碼的靈活性和類型安全性。 1)通過std::is_integral和std::is_floating_point等進行類型判斷,實現高效的類型檢查和輸出。 2)使用std::is_trivially_copyable優化vector拷貝,根據類型選擇不同的拷貝策略。 3)注意編譯時決策、類型安全、性能優化和代碼複雜性,合理使用typetraits可以大大提升代碼質量。
