欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

python與C互相調(diào)用的方法詳解

 更新時(shí)間:2017年07月14日 10:18:38   作者:人在廣州_2017  
這篇文章主要給大家介紹了關(guān)于python與C互相調(diào)用方法的相關(guān)資料,文中通過(guò)示例代碼詳細(xì)介紹了動(dòng)用的方法,對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面跟著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧。

前言

最近因?yàn)楣ぷ鞯男枰诳紤]基于udp做一個(gè)用于網(wǎng)游戰(zhàn)斗中的數(shù)據(jù)同步協(xié)議,為了前期測(cè)試數(shù)據(jù),決定先做一個(gè)外部的代理tunnel,原理是在server端和client端分別建立網(wǎng)絡(luò)轉(zhuǎn)發(fā)proxy,即原來(lái)的C/S連接改為兩個(gè)proxy之間數(shù)據(jù)快速傳輸。因?yàn)閡dp庫(kù)是用C++寫(xiě)的代碼,在測(cè)試數(shù)據(jù)的時(shí)候需要不斷地修改參數(shù),重新編譯,修改輸出統(tǒng)計(jì)數(shù)據(jù)制表等,不勝其煩,最終決定導(dǎo)出接口由python腳本來(lái)進(jìn)行邏輯調(diào)用。下面話不多說(shuō),來(lái)一起看看詳細(xì)的介紹:

C/C++導(dǎo)出到python有多種方法,根據(jù)不同的需求,可以使用下面不同的方式:

1、ctypes綁定。ctypes就包含在萬(wàn)能的python標(biāo)準(zhǔn)庫(kù)模塊里面,它可以運(yùn)行時(shí)載入動(dòng)態(tài)鏈接庫(kù)(dll,so),在CPython 2.x/3.x和PyPy上都支持。這種方式好處就是不用針對(duì)性地用python api寫(xiě)導(dǎo)出函數(shù),可以直接加載動(dòng)態(tài)鏈接庫(kù)的符號(hào)表,在python中就可以直接調(diào)用了。

2、第三方的python binding。例子有boost-python,實(shí)現(xiàn)方式是工具自動(dòng)化用Python/C api生成一系列C++ wrapper函數(shù)。特別適用于大型的庫(kù)或引擎導(dǎo)出到python。

3、手動(dòng)寫(xiě)python binding函數(shù)。如果對(duì)Python C api熟悉的話,這種方式應(yīng)該是最靈活的,讀一遍API文檔就可以使用。理論上效率應(yīng)該是最好的,但對(duì)于我這種python初學(xué)者,可能需要花上不少時(shí)間。

以之前折騰C函數(shù)導(dǎo)出到Lua腳本的經(jīng)歷,本以為要先研究一番python c api,再搞上半天才能搞定。后面發(fā)現(xiàn)python標(biāo)準(zhǔn)庫(kù)模塊的ctypes已經(jīng)非常強(qiáng)大,雖然性能應(yīng)該是三種方式里面最差的,但在這個(gè)最高60fps的tunnel里面,C/Python接口邊界調(diào)用的損耗先忽略。跟其他兩種方式設(shè)計(jì)不一樣的是,ctypes采用的是非入侵式調(diào)用接口的方式,不需要修改原來(lái)的C接口或者寫(xiě)一些綁定代碼,直接對(duì)編譯出來(lái)的動(dòng)態(tài)庫(kù)進(jìn)行調(diào)用。ctypes使用過(guò)程也是非常愉悅的。

下面介紹下ctypes的使用:

1、加載DLL動(dòng)態(tài)鏈接庫(kù)

這里需要注意區(qū)分動(dòng)態(tài)鏈接庫(kù)函數(shù)是使用cdecl還是stdcall的調(diào)用約定,分別使用cdll或windll加載動(dòng)態(tài)庫(kù)。

例如:

# 加載udp庫(kù)函數(shù) 
udp_server = cdll.LoadLibrary("./udp_server.so") 
init_udp_server = udp_server.init_udp_server 
destroy_udp_server = udp_server.destroy_udp_server 
update_udp_server = udp_server.update_udp_server 
SendMsg = udp_server.SendMsg 

SetConnectCallback = udp_server.SetConnectCallback 
SetDisconnectCallback = udp_server.SetDisconnectCallback 
SetTimeoutCallback = udp_server.SetTimeoutCallback 
SetRecvCallback = udp_server.SetRecvCallback

2、數(shù)據(jù)類型映射

除了ctypes定義的基本數(shù)據(jù)類型(c_char, c_int, c_double等),還能使用pointer函數(shù)轉(zhuǎn)換成指針類型。對(duì)于要導(dǎo)出的網(wǎng)絡(luò)庫(kù),設(shè)置回調(diào)函數(shù)是必不可少的,在C++庫(kù)里面,回調(diào)函數(shù)是通過(guò)設(shè)置一個(gè)函數(shù)指針完成的,ctypes同樣支持函數(shù)指針的聲明。如:recv_cb = CFUNCTYPE( None, c_char_p, c_int ) ,表示一個(gè)返回值為void,參數(shù)為char*和int類型的回調(diào)函數(shù)。

def __init__(self, port, ip="127.0.0.1"): 
  self._port = port 
  self._ip = ip 

  self._clients = {} 

  self.c_connect_cb = connect_cb(self.server_connect) 
  self.c_disconnect_cb = disconnect_cb(self.server_disconnect) 
  self.c_timeout_cb = timeout_cb(self.server_timeout) 
  self.c_recv_cb = recv_cb(self.server_recv) 

def create(self): 
  if self._port: 
   if init_udp_server(self._ip, self._port) == 0: 
    print "server listen %s:%d" % (self._ip, self._port) 
    SetConnectCallback( self.c_connect_cb ) 
    SetDisconnectCallback( self.c_disconnect_cb ) 
    SetTimeoutCallback( self.c_timeout_cb ) 
    SetRecvCallback( self.c_recv_cb ) 
    return True 
  print "[error] init_udp_server error", self._ip, self._port 
  return False

綁定回調(diào)參數(shù)需要注意的是,綁定的回調(diào)函數(shù)需要保存為成員變量(上面的寫(xiě)法),目的是避免python垃圾回收導(dǎo)致回調(diào)函數(shù)變成野指針。這算是一個(gè)小小的坑吧?;旧弦粋€(gè)小小的庫(kù)也就用到這些功能。

總結(jié)

以上就是這篇文章的全部?jī)?nèi)容了,希望本文的內(nèi)容對(duì)大家的學(xué)習(xí)或者工作能帶來(lái)一定的幫助,如果有疑問(wèn)大家可以留言交流,謝謝大家對(duì)腳本之家的支持。

相關(guān)文章

  • Python MySQLdb Linux下安裝筆記

    Python MySQLdb Linux下安裝筆記

    這篇文章主要介紹了Python MySQLdb Linux下安裝筆記,本文分別講解了快速安裝和手動(dòng)編譯安裝兩種方法,并分別講解了操作步驟,需要的朋友可以參考下
    2015-05-05
  • Python實(shí)現(xiàn)監(jiān)控一個(gè)程序的運(yùn)行情況

    Python實(shí)現(xiàn)監(jiān)控一個(gè)程序的運(yùn)行情況

    這篇文章主要為大家介紹了Python如何實(shí)現(xiàn)監(jiān)控一個(gè)程序的運(yùn)行情況,然后視情況將進(jìn)程殺死并重啟,文中的示例代碼簡(jiǎn)潔易懂,需要的可以參考一下
    2023-05-05
  • Python中常用的GUI(圖形用戶界面)庫(kù)用法詳細(xì)介紹

    Python中常用的GUI(圖形用戶界面)庫(kù)用法詳細(xì)介紹

    GUI圖形用戶界面是一種允許用戶通過(guò)圖形元素(如圖標(biāo)、按鈕、窗口等)與電子設(shè)備進(jìn)行交互的用戶界面,下面這篇文章主要給大家介紹了關(guān)于Python中常用的GUI(圖形用戶界面)庫(kù)用法的相關(guān)資料,需要的朋友可以參考下
    2024-08-08
  • python 根據(jù)csv表頭、列號(hào)讀取數(shù)據(jù)的實(shí)現(xiàn)

    python 根據(jù)csv表頭、列號(hào)讀取數(shù)據(jù)的實(shí)現(xiàn)

    這篇文章主要介紹了python 根據(jù)csv表頭、列號(hào)讀取數(shù)據(jù)的實(shí)現(xiàn)方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2022-05-05
  • 詳解Python如何利用pdfplumber提取PDF中的表格

    詳解Python如何利用pdfplumber提取PDF中的表格

    pdfplumber 是一個(gè)開(kāi)源的 python 工具庫(kù) ,它可以輕松的獲取 PDF 文本內(nèi)容、標(biāo)題、表格、尺寸等各種信息,今天來(lái)介紹如何使用它來(lái)提取 PDF 中的表格,文中通過(guò)代碼和圖片講解的非常詳細(xì),需要的朋友可以參考下
    2024-04-04
  • python 爬取英雄聯(lián)盟皮膚圖片

    python 爬取英雄聯(lián)盟皮膚圖片

    還記得那些年一起網(wǎng)吧開(kāi)黑通宵的日子嗎?《英雄聯(lián)盟》絕對(duì)是大學(xué)時(shí)期的風(fēng)靡游戲,即使畢業(yè)多年的大學(xué)同學(xué)相聚,難免不懷念一番當(dāng)時(shí)一起玩《英雄聯(lián)盟》的日子。今天就給大家分享一下英雄及皮膚圖片的爬蟲(chóng)。
    2021-05-05
  • 使用Python操作Excel中圖片的基礎(chǔ)示例(插入、替換、提取、刪除)

    使用Python操作Excel中圖片的基礎(chǔ)示例(插入、替換、提取、刪除)

    Excel是主要用于處理表格和數(shù)據(jù)的工具,我們也能在其中插入、編輯或管理圖片,為工作表增添視覺(jué)效果,提升報(bào)告的吸引力,本文將詳細(xì)介紹如何使用Python操作Excel中的圖片,文中有詳細(xì)代碼示例供大家參考,需要的朋友可以參考下
    2024-07-07
  • Sanic框架藍(lán)圖用法實(shí)例分析

    Sanic框架藍(lán)圖用法實(shí)例分析

    這篇文章主要介紹了Sanic框架藍(lán)圖用法,結(jié)合實(shí)例形式分析了Sanic框架中藍(lán)圖的功能以及路由控制中藍(lán)圖的定義、注冊(cè)、簡(jiǎn)單使用方法及相關(guān)操作注意事項(xiàng),需要的朋友可以參考下
    2018-07-07
  • 用Python寫(xiě)個(gè)新年賀卡生成器

    用Python寫(xiě)個(gè)新年賀卡生成器

    大家好,本篇文章主要講的是用Python寫(xiě)個(gè)新年賀卡生成器,感興趣的同學(xué)趕快來(lái)看一看吧,對(duì)你有幫助的話記得收藏一下
    2022-01-01
  • python定時(shí)任務(wù) sched模塊用法實(shí)例

    python定時(shí)任務(wù) sched模塊用法實(shí)例

    這篇文章主要介紹了python定時(shí)任務(wù) sched模塊用法實(shí)例,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2019-11-11

最新評(píng)論