在C語(yǔ)言中,字符串處理是每天都要面對(duì)的問(wèn)題。我們都知道C語(yǔ)言中其實(shí)并沒(méi)有一種原生的字符串類(lèi)型,‘字符串’在C語(yǔ)言里只是一種特殊的以''結(jié)尾的字符數(shù)組。因此,如何將C語(yǔ)言與更高層次的Python語(yǔ)言在‘字符串’處理這個(gè)問(wèn)題上對(duì)接是一個(gè)有難度的問(wèn)題。所幸有swig這種強(qiáng)大的工具。

創(chuàng)新互聯(lián)公司是專(zhuān)業(yè)的米東網(wǎng)站建設(shè)公司,米東接單;提供網(wǎng)站制作、做網(wǎng)站,網(wǎng)頁(yè)設(shè)計(jì),網(wǎng)站設(shè)計(jì),建網(wǎng)站,PHP網(wǎng)站建設(shè)等專(zhuān)業(yè)做網(wǎng)站服務(wù);采用PHP框架,可快速的進(jìn)行米東網(wǎng)站開(kāi)發(fā)網(wǎng)頁(yè)制作和功能擴(kuò)展;專(zhuān)業(yè)做搜索引擎喜愛(ài)的網(wǎng)站,專(zhuān)業(yè)的做網(wǎng)站團(tuán)隊(duì),希望更多企業(yè)前來(lái)合作!
如何封裝一個(gè)函數(shù),它修改參數(shù)字符串的內(nèi)容
假如有這樣一個(gè)C語(yǔ)言的函數(shù),
!-- lang: cpp --
void FillZero(char* pc,size_t * piLen)
{
size_t i=0;
while(i++*piLen/2 )
*pc++ = '0';
*pc = 0;
*piLen = i+1;
}
這個(gè)函數(shù)的功能是把字符串變成n個(gè)0。不過(guò)我們更關(guān)注函數(shù)的形式。這樣的函數(shù),表面上看char* pc是函數(shù)的參數(shù),可是實(shí)際上它才是函數(shù)的返回值和執(zhí)行的結(jié)果。piLen這個(gè)參數(shù)既是pc的最大長(zhǎng)度,也是新的字符串的長(zhǎng)度。我們直接用python封裝,看看運(yùn)行結(jié)果。
Type "help", "copyright", "credits" or "license" for more information.
import cchar
s='123456'
cchar.FillZero(s,6)
Traceback (most recent call last):
File "stdin", line 1, in module
TypeError: in method 'FillZero', argument 2 of type 'size_t *'
結(jié)果差強(qiáng)人意,不是我們想要得到的結(jié)果。函數(shù)的第二個(gè)參數(shù)為size_t* 我們很難用python來(lái)表示,而且python中也不存在既是輸入,也是輸出的參數(shù)。
swig有一個(gè)標(biāo)準(zhǔn)庫(kù),其中有一個(gè)cstring.i文件就是用來(lái)解決C語(yǔ)言字符串類(lèi)型的問(wèn)題。
我們?cè)?i文件中加入這樣幾行
!-- lang: cpp --
%include "cstring.i"
%cstring_output_withsize(char* pc,size_t* pi)
void FillZero(char* pc, size_t* pi);
然后運(yùn)行看結(jié)果
Type "help", "copyright", "credits" or "license" for more information.
import cchar
cchar.FillZero(10)
'00000\x00'
s=cchar.FillZero(10)
print s
00000
我們看函數(shù)的變化。首先在python里, FillZero變成了只有一個(gè)參數(shù)的函數(shù)。然后函數(shù)的返回值變成了一個(gè)字符串。其實(shí)cstring_output_size其實(shí)是一個(gè)宏,通過(guò)這個(gè)宏的定義改變了函數(shù)的形式,直接在Python中得到我們想要的結(jié)果。
其實(shí)類(lèi)似cstring_output_size的宏還有好幾個(gè),我列舉一下:
cstring_output_allocate(char *s,free($1));
第一個(gè)參數(shù)是指向字符串地址的指針,第二個(gè)參數(shù)為釋放空間的方法。
大家考慮這一下這樣的函數(shù):
void foo(char* s)
{
s = (char*)malloc(10);
memcpy(s,"123456789",9);
}
s這個(gè)參數(shù)表面上看是輸入,實(shí)際上是函數(shù)真正的輸出。 函數(shù)中真正改變的東西是chars指向的字符串的值。而且char這個(gè)類(lèi)型,
python或者其他腳本語(yǔ)言里應(yīng)該都沒(méi)有對(duì)應(yīng)的類(lèi)型。那么我們用cstring_output_allocate將這個(gè)函數(shù)轉(zhuǎn)換成另外一個(gè)形式的python或者其他腳本語(yǔ)言的函數(shù)。轉(zhuǎn)換后的函數(shù)其實(shí)是這樣的,以python為例str
foo()。
!-- lang: cpp --
%module a
%include "cstring.i"
%{
void foo(char* s);
%}
%cstring_output_allocate(char *s, free(*$1));
void foo(char *s);
在python中的調(diào)用:
!-- lang: python --
import a
a.foo()
'123456789'
cstring_output_maxsize(char *path, int maxpath);
第一個(gè)參數(shù)也是可以改變的字符串首地址,第二個(gè)參數(shù)為字符串的最大長(zhǎng)度。在Python中調(diào)用的時(shí)候,只有maxpath這個(gè)參數(shù),返回字符串。
cstring_output_allocate(char *s, free($1));
第一個(gè)參數(shù)為指向字符串首地址的指針,第二個(gè)參數(shù)為釋放指針的方法。這個(gè)宏主要是封裝一種直接在函數(shù)內(nèi)部malloc空間的函數(shù)。在Python中調(diào)用時(shí)沒(méi)有參數(shù),直接返回字符串。
cstring_output_allocate_size(char *s, int slen, free(*$1));
這個(gè)相當(dāng)于前面兩個(gè)函數(shù)的組合。在函數(shù)內(nèi)部malloc空間,然后將字符串長(zhǎng)度通過(guò)slen返回。其實(shí)在調(diào)用的時(shí)候非常簡(jiǎn)單,沒(méi)有參數(shù),直接返回字符串。
如何處理c++的std::string
std::string是C++標(biāo)準(zhǔn)類(lèi)庫(kù)STL中常見(jiàn)的類(lèi)。在平時(shí)工作中大家肯定是沒(méi)少用。在python中如何封裝std::string? swig提供了標(biāo)準(zhǔn)庫(kù)
例如函數(shù):
!-- lang: cpp --
string Repeat(const string s)
{
return s+s;
}
只要在swig中加入這樣幾行:
!-- lang: cpp --
%include "std_string.i"
using namespace std;
string Repeat(const string s);
運(yùn)行結(jié)果:
Python 2.6.6 (r266:84292, Dec 27 2010, 00:02:40)
[GCC 4.4.5] on linux2
Type "help", "copyright", "credits" or "license" for more information.
import cchar
cchar.Repeat('123')
'123123'
使用起來(lái)很方便,但需要注意的是,假如函數(shù)的參數(shù)的內(nèi)容是可以被修改,就不能用這種方式封裝。
例如:
!-- lang: cpp --
void repeat(string s)
{
s+=s;
}
這樣的函數(shù)直接使用 'std_string.i' 就是無(wú)效的。遇到這種函數(shù),只能用C語(yǔ)言封裝成 void repeat(chars, int maxsize), 再用swig調(diào)用 'cstring_output_withsize' 這個(gè)宏再封裝一次了。
xlwings是Python處理Excel的有力工具,xlwings的強(qiáng)大之處是可以調(diào)用vba里面的宏和各種函數(shù)。由于考慮到數(shù)據(jù)的安全性問(wèn)題,宏在大部分的Excel文件當(dāng)中是不可以被執(zhí)行的。儲(chǔ)備能夠執(zhí)行的宏的Excel一般是xlmt。Python跨工作簿調(diào)用宏是需要做一系列處理,需求傳遞工作表信息到宏才能執(zhí)行。傳遞完成了,基本上vba里面宏錄制的各種操作都可以批量執(zhí)行。
python是單線(xiàn)程的,所以做圖形界面都很挫,直接用xlwings吧,打開(kāi)的excel就是界面,可以excel函數(shù)調(diào)用py,也可以py調(diào)用宏
當(dāng)前文章:python宏與函數(shù),python有宏定義嗎
標(biāo)題來(lái)源:http://chinadenli.net/article22/dsipgjc.html
成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供網(wǎng)站內(nèi)鏈、手機(jī)網(wǎng)站建設(shè)、自適應(yīng)網(wǎng)站、外貿(mào)建站、移動(dòng)網(wǎng)站建設(shè)、網(wǎng)站改版
聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶(hù)投稿、用戶(hù)轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請(qǐng)盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如需處理請(qǐng)聯(lián)系客服。電話(huà):028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來(lái)源: 創(chuàng)新互聯(lián)
全網(wǎng)營(yíng)銷(xiāo)推廣知識(shí)