找回密码
 会员注册
查看: 11|回复: 0

Linux下跨语言调用C++实践

[复制链接]

2万

主题

0

回帖

7万

积分

超级版主

积分
72377
发表于 2024-10-6 12:36:58 | 显示全部楼层 |阅读模式
总第504篇2022年 第021篇不同的开发语言适合不同的领域,例如Python适合做数据分析,C++适合做系统的底层开发,假如它们需要用到相同功能的基础组件,组件使用多种语言分别开发的话,不仅增加了开发和维护成本,而且不能确保多种语言间在处理效果上是一致的。本文以美团搜索实际场景下的案例,讲述在Linux系统下跨语言调用的实践,即开发一次C++语言的组件,其他语言通过跨语言调用技术调用C++组件。1 背景介绍2 方案概述3 实现详情3.1 功能代码3.2 打包发布3.3 业务使用3.4 易用性优化4. 原理介绍4.1 为什么需要一个c_wrapper4.2 跨语言调用如何实现参数传递4.3 扩展阅读(JNA直接映射)4.4 性能分析5 应用案例5.1 离线任务中的应用5.2 在线服务中的应用6 总结1 背景查询理解(QU, Query Understanding)是美团搜索的核心模块,主要职责是理解用户查询,生成查询意图、成分、改写等基础信号,应用于搜索的召回、排序、展示等多个环节,对搜索基础体验至关重要。该服务的线上主体程序基于C++语言开发,服务中会加载大量的词表数据、预估模型等,这些数据与模型的离线生产过程有很多文本解析能力需要与线上服务保持一致,从而保证效果层面的一致性,如文本归一化、分词等。而这些离线生产过程通常用Python与Java实现。如果在线、离线用不同语言各自开发一份,则很难维持策略与效果上的统一。同时这些能力会有不断的迭代,在这种动态场景下,不断维护多语言版本的效果打平,给我们的日常迭代带来了极大的成本。因此,我们尝试通过跨语言调用动态链接库的技术解决这个问题,即开发一次基于C++的so,通过不同语言的链接层封装成不同语言的组件库,并投入到对应的生产过程。这种方案的优势非常明显,主体的业务逻辑只需要开发一次,封装层只需要极少量的代码,主体业务迭代升级,其它语言几乎不需要改动,只需要包含最新的动态链接库,发布最新版本即可。同时C++作为更底层的语言,在很多场景下,它的计算效率更高,硬件资源利用率更高,也为我们带来了一些性能上的优势。本文对我们在实际生产中尝试这一技术方案时,遇到的问题与一些实践经验做了完整的梳理,希望能为大家提供一些参考或帮助。2 方案概述为了达到业务方开箱即用的目的,综合考虑C++、Python、Java用户的使用习惯,我们设计了如下的协作结构:图 13 实现详情Python、Java支持调用C接口,但不支持调用C++接口,因此对于C++语言实现的接口,必须转换为C语言实现。为了不修改原始C++代码,在C++接口上层用C语言进行一次封装,这部分代码通常被称为“胶水代码”(Glue Code)。具体方案如下图所示:图 2本章节各部分内容如下:【功能代码】部分,通过打印字符串的例子来讲述各语言部分的编码工作。【打包发布】部分,介绍如何将生成的动态库作为资源文件与Python、Java代码打包在一起发布到仓库,以降低使用方的接入成本。【业务使用】部分,介绍开箱即用的使用示例。【易用性优化】部分,结合实际使用中遇到的问题,讲述了对于Python版本兼容,以及动态库依赖问题的处理方式。3.1 功能代码3.1.1 C++代码作为示例,实现一个打印字符串的功能。为了模拟实际的工业场景,对以下代码进行编译,分别生成动态库 libstr_print_cpp.so、静态库libstr_print_cpp.a。str_print.h#pragma?once#include?class?StrPrint?{?public:????void?print(const?std::string&?text);};str_print.cpp#include?#include?"str_print.h"void?StrPrint::print(const?std::string&?text)?{????std::cout?<
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 会员注册

本版积分规则

QQ|手机版|心飞设计-版权所有:微度网络信息技术服务中心 ( 鲁ICP备17032091号-12 )|网站地图

GMT+8, 2025-1-11 13:04 , Processed in 0.779405 second(s), 25 queries .

Powered by Discuz! X3.5

© 2001-2025 Discuz! Team.

快速回复 返回顶部 返回列表