日韩无码专区无码一级三级片|91人人爱网站中日韩无码电影|厨房大战丰满熟妇|AV高清无码在线免费观看|另类AV日韩少妇熟女|中文日本大黄一级黄色片|色情在线视频免费|亚洲成人特黄a片|黄片wwwav色图欧美|欧亚乱色一区二区三区

RELATEED CONSULTING
相關(guān)咨詢
選擇下列產(chǎn)品馬上在線溝通
服務(wù)時間:8:30-17:00
你可能遇到了下面的問題
關(guān)閉右側(cè)工具欄

新聞中心

這里有您想知道的互聯(lián)網(wǎng)營銷解決方案
創(chuàng)新互聯(lián)Python教程:4.構(gòu)建C/C++擴展

4. 構(gòu)建C/C++擴展

一個Cpython的C擴展是一個共享庫(例如一個Linux上的 .so ,或者Windows上的 .pyd ),其會導(dǎo)出一個 初始化函數(shù)

專注于為中小企業(yè)提供成都網(wǎng)站制作、成都做網(wǎng)站服務(wù),電腦端+手機端+微信端的三站合一,更高效的管理,為中小企業(yè)宿州免費做網(wǎng)站提供優(yōu)質(zhì)的服務(wù)。我們立足成都,凝聚了一批互聯(lián)網(wǎng)行業(yè)人才,有力地推動了近千家企業(yè)的穩(wěn)健成長,幫助中小企業(yè)通過網(wǎng)站建設(shè)實現(xiàn)規(guī)模擴充和轉(zhuǎn)變。

為了可導(dǎo)入,共享庫必須在 PYTHONPATH 中有效,且必須命名遵循模塊名字,通過適當?shù)臄U展。當使用distutils時,會自動生成正確的文件名。

初始化函數(shù)的聲明如下:

PyObject *PyInit_modulename(void)

It returns either a fully initialized module, or a PyModuleDef instance. See 初始化 C 模塊 for details.

對于僅有ASCII編碼的模塊名,函數(shù)必須是 PyInit_ ,將 替換為模塊的名字。當使用 Multi-phase initialization 時,允許使用非ASCII編碼的模塊名。此時初始化函數(shù)的名字是 PyInitU_ ,而 需要用Python的 punycode 編碼,連字號需替換為下劃線。在Python里:

 
 
 
 
  1. def initfunc_name(name):
  2. try:
  3. suffix = b'_' + name.encode('ascii')
  4. except UnicodeEncodeError:
  5. suffix = b'U_' + name.encode('punycode').replace(b'-', b'_')
  6. return b'PyInit' + suffix

可以在一個動態(tài)庫里導(dǎo)出多個模塊,通過定義多個初始化函數(shù)。而導(dǎo)入他們需要符號鏈接或自定義導(dǎo)入器,因為缺省時只有對應(yīng)了文件名的函數(shù)才會被發(fā)現(xiàn)。查看 “一個庫里的多模塊” 章節(jié),在 PEP 489 了解更多細節(jié)。

4.1. 使用distutils構(gòu)建C和C++擴展

擴展模塊可以用distutils來構(gòu)建,這是Python自帶的。distutils也支持創(chuàng)建二進制包,用戶無需編譯器而distutils就能安裝擴展。

一個distutils包包含了一個驅(qū)動腳本 setup.py 。這是個純Python文件,大多數(shù)時候也很簡單,看起來如下:

 
 
 
 
  1. from distutils.core import setup, Extension
  2. module1 = Extension('demo',
  3. sources = ['demo.c'])
  4. setup (name = 'PackageName',
  5. version = '1.0',
  6. description = 'This is a demo package',
  7. ext_modules = [module1])

通過文件 setup.py ,和文件 demo.c ,運行如下

 
 
 
 
  1. python setup.py build

這會編譯 demo.c ,然后產(chǎn)生一個擴展模塊叫做 demo 在目錄 build 里。依賴于系統(tǒng),模塊文件會放在某個子目錄形如 build/lib.system ,名字可能是 demo.sodemo.pyd 。

在文件 setup.py 里,所有動作的入口通過 setup 函數(shù)。該函數(shù)可以接受可變數(shù)量個關(guān)鍵字參數(shù),上面的例子只使用了一個子集。特別需要注意的例子指定了構(gòu)建包的元信息,以及指定了包內(nèi)容。通常一個包會包括多個模塊,就像Python的源碼模塊、文檔、子包等。請參數(shù)distutils的文檔,在 分發(fā) Python 模塊(遺留版本) 來了解更多distutils的特性;本章節(jié)只解釋構(gòu)建擴展模塊的部分。

通常預(yù)計算參數(shù)給 setup() ,想要更好的結(jié)構(gòu)化驅(qū)動腳本。有如如上例子函數(shù) setup() 的 ext_modules 參數(shù)是一列擴展模塊,每個是一個 Extension 類的實例。例子中的實例定義了擴展命名為 demo ,從單一源碼文件構(gòu)建 demo.c 。

更多時候,構(gòu)建一個擴展會復(fù)雜的多,需要額外的預(yù)處理器定義和庫。如下例子展示了這些。

 
 
 
 
  1. from distutils.core import setup, Extension
  2. module1 = Extension('demo',
  3. define_macros = [('MAJOR_VERSION', '1'),
  4. ('MINOR_VERSION', '0')],
  5. include_dirs = ['/usr/local/include'],
  6. libraries = ['tcl83'],
  7. library_dirs = ['/usr/local/lib'],
  8. sources = ['demo.c'])
  9. setup (name = 'PackageName',
  10. version = '1.0',
  11. description = 'This is a demo package',
  12. author = 'Martin v. Loewis',
  13. author_email = 'martin@v.loewis.de',
  14. url = 'https://docs.python.org/extending/building',
  15. long_description = '''
  16. This is really just a demo package.
  17. ''',
  18. ext_modules = [module1])

例子中函數(shù) setup() 在調(diào)用時額外傳遞了元信息,是推薦發(fā)布包構(gòu)建時的內(nèi)容。對于這個擴展,其指定了預(yù)處理器定義,include目錄,庫目錄,庫。依賴于編譯器,distutils還會用其他方式傳遞信息給編譯器。例如在Unix上,結(jié)果是如下編譯命令

 
 
 
 
  1. gcc -DNDEBUG -g -O3 -Wall -Wstrict-prototypes -fPIC -DMAJOR_VERSION=1 -DMINOR_VERSION=0 -I/usr/local/include -I/usr/local/include/python2.2 -c demo.c -o build/temp.linux-i686-2.2/demo.o
  2. gcc -shared build/temp.linux-i686-2.2/demo.o -L/usr/local/lib -ltcl83 -o build/lib.linux-i686-2.2/demo.so

這些行代碼僅用于展示目的;distutils用戶應(yīng)該相信distutils能正確調(diào)用。

4.2. 發(fā)布你的擴展模塊

當一個擴展已經(jīng)成功地被構(gòu)建時,有三種方式來使用它。

最終用戶通常想要安裝模塊,可以這么運行

 
 
 
 
  1. python setup.py install

模塊維護者應(yīng)該制作源碼包;要實現(xiàn)可以運行

 
 
 
 
  1. python setup.py sdist

有些情況下,需要在源碼發(fā)布包里包含額外的文件;這通過 MANIFEST.in 文件實現(xiàn),查看 指定要分發(fā)的文件 了解細節(jié)。

如果源碼發(fā)行包被成功地構(gòu)建,維護者還可以創(chuàng)建二進制發(fā)行包。 取決于具體平臺,以下命令中的一個可以用來完成此任務(wù)

 
 
 
 
  1. python setup.py bdist_rpm
  2. python setup.py bdist_dumb

文章標題:創(chuàng)新互聯(lián)Python教程:4.構(gòu)建C/C++擴展
文章URL:http://www.5511xx.com/article/cdiepgp.html