热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

用PHP的FFI调用cjieba

使用PHP7.4的FFI测试直接调用cjieba分词的动态库,选用CJieba的原因是FFI使用的是C的调用约定,如果用Cpp,还得自己包装一下,然后externC,让编译器生成标准C的动态库。
推荐:《PHP视频教程》

phpjieba_ffi

使用PHP 7.4的 FFI 测试直接调用cjieba分词的动态库

选用CJieba的原因是FFI使用的是C的调用约定,如果用Cpp,还得自己包装一下,然后extern C,让编译器生成标准C的动态库。

碰到的问题

段错误

C变量没有初始化

直接调用了C的函数,没有通过FFI 初始化后的的C对象调用

非空判断 需要使用 FFI::isNull($x)

指针形式的数组 不能用foreach

指针形式数组的循环

查看C代码发现Cut部分如下:

CJiebaWord* Cut(Jieba handle, const char* sentence, size_t len) {
  cppjieba::Jieba* x = (cppjieba::Jieba*)handle;
  vector words;
  string s(sentence, len);
  x->Cut(s, words);
  
  CJiebaWord* res = (CJiebaWord*)malloc(sizeof(CJiebaWord) * (words.size() + 1));
  size_t offset = 0;
  for (size_t i = 0; i 

返回的是一个结构体指针,在C语言里,数组名实际是数组第一个变量的指针地址,所以可以通过指针地址++的操作来遍历,在FFI里面呢?

对于这个数组,我一开始用foreach 循环,直接报段错误了,后来和C一样,直接用指针++,发现是可行的,这里给FFI点赞,居然也可以直接操作C指针。

分词结果获取

如上面的代码,对于单个分词CJiebaWord,也不是保存的分词,而是sentence + offset,就是说第一个分词结果肯定是原始字符串。

在C的demo里是printf格式化(. 表示字段宽度和对齐),但是PHP里没有类似的方法,需要截取字符串substr($x->word, 0, $x->len)

  for (x = words; x->word; x++) {
    printf("%*.*s\n", x->len, x->len, x->word);
  }

用法示例

编译动态库

make libjieba.so

运行

time php demo.php

运行c demo

make demo
time ./demo

结果

PHP
load: 0.00025701522827148
real    1m59.619s
user    1m56.093s
sys     0m3.517s
C
real    1m54.738s
user    1m50.382s
sys     0m4.323s
CPU 占用 基本都是 12%

可以发现使用FFI,PHP的速度基本和C差不多,如有CPU占用大的业务,可以尝试使用其它语言(C/C++,golang,Rust等)编写然后导出标准C的动态库。

FFI的用途

在没有FFI之前,需要系统调用或者sdk方式调用的地方,PHP就需要开发扩展,但是开发扩展不仅需要理解C语言,还得了解PHP内核,比较困难。 现在就方便多了,直接使用FFI调用动态库即可。

扩展 宏展开

比如海康的sdk里有大量的宏 gcc -E -P HCNetSDK.h -o HCNetSDK_unfold.h 支持 type define 放心使用

原文地址:https://github.com/dwdcth/phpjieba_ffi

以上就是用PHP的FFI调用cjieba的详细内容,更多请关注其它相关文章!


推荐阅读
  • 在Docker中,将主机目录挂载到容器中作为volume使用时,常常会遇到文件权限问题。这是因为容器内外的UID不同所导致的。本文介绍了解决这个问题的方法,包括使用gosu和suexec工具以及在Dockerfile中配置volume的权限。通过这些方法,可以避免在使用Docker时出现无写权限的情况。 ... [详细]
  • 初探PLC 的ST 语言转换成C++ 的方法
    自动控制软件绕不开ST(StructureText)语言。它是IEC61131-3标准中唯一的一个高级语言。目前,大多数PLC产品支持ST ... [详细]
  • 云原生边缘计算之KubeEdge简介及功能特点
    本文介绍了云原生边缘计算中的KubeEdge系统,该系统是一个开源系统,用于将容器化应用程序编排功能扩展到Edge的主机。它基于Kubernetes构建,并为网络应用程序提供基础架构支持。同时,KubeEdge具有离线模式、基于Kubernetes的节点、群集、应用程序和设备管理、资源优化等特点。此外,KubeEdge还支持跨平台工作,在私有、公共和混合云中都可以运行。同时,KubeEdge还提供数据管理和数据分析管道引擎的支持。最后,本文还介绍了KubeEdge系统生成证书的方法。 ... [详细]
  • MACElasticsearch安装步骤及验证方法
    本文介绍了MACElasticsearch的安装步骤,包括下载ZIP文件、解压到安装目录、启动服务,并提供了验证启动是否成功的方法。同时,还介绍了安装elasticsearch-head插件的方法,以便于进行查询操作。 ... [详细]
  • 推荐系统遇上深度学习(十七)详解推荐系统中的常用评测指标
    原创:石晓文小小挖掘机2018-06-18笔者是一个痴迷于挖掘数据中的价值的学习人,希望在平日的工作学习中,挖掘数据的价值, ... [详细]
  • Google Play推出全新的应用内评价API,帮助开发者获取更多优质用户反馈。用户每天在Google Play上发表数百万条评论,这有助于开发者了解用户喜好和改进需求。开发者可以选择在适当的时间请求用户撰写评论,以获得全面而有用的反馈。全新应用内评价功能让用户无需返回应用详情页面即可发表评论,提升用户体验。 ... [详细]
  • Java验证码——kaptcha的使用配置及样式
    本文介绍了如何使用kaptcha库来实现Java验证码的配置和样式设置,包括pom.xml的依赖配置和web.xml中servlet的配置。 ... [详细]
  • FeatureRequestIsyourfeaturerequestrelatedtoaproblem?Please ... [详细]
  • 本文介绍了Linux Shell中括号和整数扩展的使用方法,包括命令组、命令替换、初始化数组以及算术表达式和逻辑判断的相关内容。括号中的命令将会在新开的子shell中顺序执行,括号中的变量不能被脚本余下的部分使用。命令替换可以用于将命令的标准输出作为另一个命令的输入。括号中的运算符和表达式符合C语言运算规则,可以用在整数扩展中进行算术计算和逻辑判断。 ... [详细]
  • 树莓派语音控制的配置方法和步骤
    本文介绍了在树莓派上实现语音控制的配置方法和步骤。首先感谢博主Eoman的帮助,文章参考了他的内容。树莓派的配置需要通过sudo raspi-config进行,然后使用Eoman的控制方法,即安装wiringPi库并编写控制引脚的脚本。具体的安装步骤和脚本编写方法在文章中详细介绍。 ... [详细]
  • 开发笔记:Python之路第一篇:初识Python
    篇首语:本文由编程笔记#小编为大家整理,主要介绍了Python之路第一篇:初识Python相关的知识,希望对你有一定的参考价值。Python简介& ... [详细]
  • 本文介绍了设计师伊振华受邀参与沈阳市智慧城市运行管理中心项目的整体设计,并以数字赋能和创新驱动高质量发展的理念,建设了集成、智慧、高效的一体化城市综合管理平台,促进了城市的数字化转型。该中心被称为当代城市的智能心脏,为沈阳市的智慧城市建设做出了重要贡献。 ... [详细]
  • 本文介绍了数据库的存储结构及其重要性,强调了关系数据库范例中将逻辑存储与物理存储分开的必要性。通过逻辑结构和物理结构的分离,可以实现对物理存储的重新组织和数据库的迁移,而应用程序不会察觉到任何更改。文章还展示了Oracle数据库的逻辑结构和物理结构,并介绍了表空间的概念和作用。 ... [详细]
  • 本文主要解析了Open judge C16H问题中涉及到的Magical Balls的快速幂和逆元算法,并给出了问题的解析和解决方法。详细介绍了问题的背景和规则,并给出了相应的算法解析和实现步骤。通过本文的解析,读者可以更好地理解和解决Open judge C16H问题中的Magical Balls部分。 ... [详细]
  • 生成对抗式网络GAN及其衍生CGAN、DCGAN、WGAN、LSGAN、BEGAN介绍
    一、GAN原理介绍学习GAN的第一篇论文当然由是IanGoodfellow于2014年发表的GenerativeAdversarialNetworks(论文下载链接arxiv:[h ... [详细]
author-avatar
达达2502854565
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有