使用C语言扩展Python(三)

上一篇中我们已经了解如何在Python程序和C模块之间进行值的相互传递,现在我们来进入实作阶段,看看如何将一个C语言开发的开源mp3编解码库LAME包装为一个Python下可以使用的扩展模块。
首先去http://lame.sourceforge.net/download.php下载LAME的源代码,然后切换到root用户编译源代码,
<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />--> ./ configure
make
makeinstall

安装完成后你可以在/usr/local/include/lame目录下找到lame.h头文件,我们在后面的demo程序中会include它的,下面就是一个非常简单的lame示例程序lame_test.c:

ExpandedBlockStart.gif 代码
<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />--> #include < stdio.h >
#include
< stdlib.h >
#include
< lame.h >

#define INBUFSIZE4096
#define MP3BUFSIZE(int)(1.25*INBUFSIZE)+7200

int encode( char * inPath, char * outPath){
int status = 0 ;
lame_global_flags
* gfp;
int ret_code;
FILE
* infp;
FILE
* outfp;
short * input_buffer;
int input_samples;
char * mp3_buffer;
int mp3_bytes;

gfp
= lame_init();
if (gfp == NULL){
printf(
" lame_initfailed/n " );
status
= - 1 ;
goto exit;
}

ret_code
= lame_init_params(gfp);
if (ret_code < 0 ){
printf(
" lame_init_paramsreturned%d/n " ,ret_code);
status
= - 1 ;
goto close_lame;
}

infp
= fopen(inPath, " rb " );
outfp
= fopen(outPath, " wb " );

input_buffer
= ( short * )malloc(INBUFSIZE * 2 );
mp3_buffer
= ( char * )malloc(MP3BUFSIZE);

do {
input_samples
= fread(input_buffer, 2 ,INBUFSIZE,infp);
mp3_bytes
= lame_encode_buffer_interleaved(gfp,input_buffer,input_samples / 2 ,mp3_buffer,MP3BUFSIZE);
if (mp3_bytes < 0 ){
printf(
" lame_encode_buffer_interleavedreturned%d/n " ,mp3_bytes);
status
= - 1 ;
goto free_buffers;
}
else if (mp3_bytes > 0 ){
fwrite(mp3_buffer,
1 ,mp3_bytes,outfp);
}
}
while (input_samples == INBUFSIZE);

mp3_bytes
= lame_encode_flush(gfp,mp3_buffer, sizeof (mp3_buffer));
if (mp3_bytes > 0 ){
printf(
" writing%dmp3bytes/n " ,mp3_bytes);
fwrite(mp3_buffer,
1 ,mp3_bytes,outfp);
}
free_buffers:
free(mp3_buffer);
free(input_buffer);

fclose(outfp);
fclose(infp);
close_lame:
lame_close(gfp);
exit:
return status;
}

int main( int argc, char ** argv){
if (argc < 3 ){
printf(
" usage:lame_testrawinfilemp3outfile/n " );
}
encode(argv[
1 ],argv[ 2 ]);
return 0 ;
}

编译步骤:

<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />--> gcc-I / usr / local / include / lamelame_test . c-lmp3lame-olame_test

试验准备:

首先需要一个test.wav文件,先安装sox来将wav文件转为raw格式的数据:

<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />--> sudoapt-getinstallsox
soxtest
. wav-trawtest . raw

然后执行lame_test来对其进行mp3编码:

<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />--> ./ lame_test ./ test . raw ./ test . mp3

好了,现在我们要在这个c程序的基础上将其包装为一个Python扩展模块。下面的pylame.c就是简单地调用lame_test.c中定义的encode方法,然后通过它对外部的python程序提高mp3编码的服务

ExpandedBlockStart.gif 代码
<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />--> #include < Python.h >
#include < lame.h >

int encode( char * , char * );

static PyObject * pylame_encode(PyObject * self,PyObject * args){
int status;
char * inPath;
char * outPath;
if ( ! PyArg_ParseTuple(args, " ss " , & inPath, & outPath)){
return NULL;
}
status = encode(inPath,outPath);
return Py_BuildValue( " i " ,status);
}

static PyMethodDefpylame_methods[] = {
{ " encode " ,pylame_encode,METH_VARARGS,NULL},
{NULL,NULL, 0 ,NULL}
};

PyMODINIT_FUNCinitpylame(){
Py_InitModule3( " pylame " ,pylame_methods, " ansimplelamemodule. " );
}

模块编译步骤:

<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />--> gcc-shared-I / usr / include / python2 . 6 -I / usr / local / include / lame / pylame . clame_test . c-lmp3lame-opylame . so

ok,现在lame扩展模块已经封装好了,可以到python程序中进行调用了。在pylame.so所在目录下新建一个python文件lame1.py代码如下:

<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />--> import pylame

if __name__ == ' __main__ ' :
inPath = ' ./test.raw '
outPath = ' ./test.mp3 '
pylame.encode(inPath,outPath)

编译执行:

<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />--> python ./ lame1 . py

你会发现生成了一个test.mp3,打开听听看是否是你想要的歌曲呢,呵呵。。。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值