跨语⾔和跨编译器的那些坑(CPythonvsIronPython)
代码是宝贵的,世界上最郁闷的事情,便是写好的代码,还要在另外的平台上重写⼀次,或是同时维护功能相同的两套代码。所以才需要跨平台。
不仅如此,⽐如有⼈会吐槽Python的原⽣解释器CPython跑得太慢,或想让Python在.NET或JAVA虚拟机上运⾏,便开发了IronPython和Jython这样的⼯具。
Jython我并不了解,就说说Irpy吧,开放源代码,并有动态语⾔运⾏时(DLR)加持,这样⽜逼的代码焉有不看?!于是看了⼩⼀个礼拜,云⾥雾⾥,确实还是⾃⼰能⼒有限。
跨语⾔
回到之前“最郁闷的问题”,我写了⼀个功能不错的数据清洗类库,有Python和C#两个版本,数据清洗的流程是⽤xml定义的,之前这样设计,就是为了跨平台和语⾔。打个⽐⽅,当我设计好⼀个清洗流程后,就可以交给C#或者Python去执⾏了。听起来是不是很美好?
c语言编译器怎么用不了我很感慨Python的强⼤能⼒,通过元类,动态添加属性等特性,我把C#将近5000⾏的代码,被Python⽤300⾏不到的规模基本实现了。不少⼈可能会好奇这是怎么做到的。C#有⿇烦的继承语法,⽽不同的类只是核⼼函数不同。⽽Py我只定义了核⼼函数,然后动态添加属性⽣成类,不少不需要实现的接⼝根本就不
⽤关⼼,再加上Py本⾝⽐Linq还骚的⽣成器语法,这样压缩⾃然是情理之中。
然⽽,蛋疼的问题出现了。
因为两种语⾔都引⽤了第三⽅的html解析类库,分别是C#的HtmlAgilityPack,和Python的lxml, 然⽽两种类库对于XPath的解析是有细微区别的,如是否有form标签,导致能被C#解析的却不能被Py解析!真是⽇了狗了!
我准备写XPath的转换函数,然⽽发现这是个⽆底洞,不同的html都有细微区别。还有C#已经完善的⾃动登录功能,我却还需要在Python的海洋⾥查对应的相似函数。
那怎么办呢?我讨厌同时维护两种语⾔的代码,那就放弃⼀边吧!
跨编译器
换在三年前,我肯定是放弃Python⽽去接着开发C#(我确实有类似处⼥座的强迫症,因噎废⾷),但如今,我被py漂亮的语法和众多第三⽅包倾倒,明显优先⽀持Py。
我想到了IronPython,这是.NET平台下能够运⾏Python的⼀套引擎,能够很⽅便地让C#和Python集成。这下简单了吧?我⽤Python实现核⼼代码,再⽤C#包装到外部界⾯上,那么就同时满⾜了⼀切需求!
然⽽,蛋疼的问题接着出现。。。。
IronPython的性能还是不错的,甚⾄运⾏起来⽐CPython还快!但是,回到那个解析html的Python类库,让Iron去执⾏引⽤lxml的Python代码是会出错的。翻遍了国内外论坛,⼤致意思是lxml(包括scipy和numpy)为了速度考虑,都是c语⾔扩展,⽽ironpython是不⽀持c语⾔扩展的模块的,所以,ironpython下不能使⽤lxml!
呵呵。
强迫症再⼀次发作,。我能怎么做?给lxml写⼀个纯Python的版本?或是,去研究某个能够⽀持IronPython⽀持c语⾔扩展的⼯具?每个任务都不简单,理性告诉,耗在这件事情上没有意义。
跨平台的意义:折腾
这就是⼯程脆弱性,⼀旦某个接⼝对不上了,整个类库都没法使⽤了。即使是python这样的语⾔,在2和3两种版本之间都让⼈颇为头疼。纵然有IronPython这种微软官⽅⽀持的强⼤⼯具,也充其量只能为⼀个玩具。原因很简单,在不同的底层基础上实现完全相同的上层,这是⾮常有难度的,⼀点点细微的区别,就会导致上层⾏为上的巨⼤不同。⽐如Python的⽣成器语法,在IronPython上就有问题。报出的错误让⼈匪夷所思,根本不知道怎么修改。
做编译器的⼈,⾃然是⼿握重剑,哪⾥不对改哪⾥。但我们这些⼩⽩怎么办,还要去搬砖呢!
这也是开源的重要性,万不得已,还能够去修改源代码。也是“使⽤被反复验证的稳定⼯具”的重要性,不要去使⽤莫名其妙的编译器/⼯具,否则本来应该思考美好的算法,⽽现在却在错误代码的海洋中抓破脑袋。⼀些新技术⾮常不确定,甚⾄已经停⽌维护,把时间浪费在这些事情上不值得的。
这也是⼯程的痛苦,也是⼯程的美妙。做研究的⼈,写了⼏⾏公式完事了,做⼯程的⼈,却不得不思考各种细节,从综合成本和效率的⾓度去做,做⼯程的⼈如果也是偏执狂,那他早就死掉了。
结语
那我还能怎么做呢?那就先这样吧,数据抓取/清洗继续⽤C#,分析⽤Python,清晰的分割线,中间⽤“利万物⽽不争”的⽂本做存储,让它们亲密接触的事情,再放放吧。
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论