通过实例浅析Python对比C语言的编程思想差异

我一直使用 Python,用它处理各种数据科学项目。 Python 以易用闻名。有编码经验者学习数天就能上手(或有效使用它)。
听起来很不错,不过,如果你既用 Python,同时也是用其他语言,比如说 C 的话,或许会存在一些问题。
给你举个我自己经历的例子吧。 我精通命令式语言,如 C 和 C 。对古老经典的语言如 Lisp 和 Prolog 能熟练使用。另外,我也用过 Java,Javascript 和 PHP 一段时间。(那么,学习) Python 对我来讲不是很简单吗?事实上,只是看起来容易,我给自己挖了个坑:我像用 C 一样去用 Python。
具体情况,请向下看。
一个最近的项目中,需要处理地理空间数据。给出(任务)是 gps 追踪 25,000 个左右位置点,需要根据给定的经纬度,重复定位距离最短的点。我第一反应是,翻查(已经实现的)计算已知经纬度两点间距离的代码片段。代码可以在 John D. Cook 写的这篇 code available in the public domain 中找得到。
万事俱备! 只要写一段 Python 函数,返回与输入坐标距离最短的点索引(25,000 点数组中的索引),就万事大吉了:    
def closest_distance(lat,lon,trkpts):
  d = 100000.0
  best = -1
  r = trkpts.index
  for i in r:
    lati = trkpts.ix[i,'Lat']
    loni = trkpts.ix[i,'Lon']
    md = distance_on_unit_sphere(lat, lon, lati, loni)
    if d > md
      best = i
      d = md
  return best
其中, distance_on_unit_sphere 是 John D. Cook's 书中的函数,trkpts 是数组,包含 gps 追踪的点坐标(实际上,是 pandas 中的数据帧,注,pandas 是 python 第三方数据分析扩展包)。
上述函数与我以前用 C 实现的函数基本相同。 它遍历(迭代)trkpts 数组,将迄今为止(距离给定坐标位置)的距离最短的点索引值,保存到本地变量 best 中。
目前为止,情况还不错,虽然 Python 语法与 C 有很多差别,但写这段代码,并没有花去我太多时间。
代码写起来快,但执行起来却很慢。例如,我指定428 个点,命名为waypoints(导航点,路点,导航路线中的关键点)。导航时,我要为每个导航点 waypoint 找出距离最短的点。为 428 个导航点 waypoint 查找距离最短点的程序,在我的笔记本上运行了 3 分 6 秒。
之后,我改为查询计算曼哈坦距离,这是近似值。我不再计算两点间的精确距离,而是计算东西轴距离和南北轴距离。计算曼哈坦距离的函数如下:    
def manhattan_distance(lat1, lon1, lat2, lon2):
  lat = (lat1 lat2)/2.0
  return abs(lat1-lat2) abs(math.cos(math.radians(lat))*(lon1-lon2))

实际上,我用了一个更简化的函数,忽略一个因素,即维度曲线上 1 度差距比经度曲线上的 1 度差距要大得多。简化函数如下:    
def manhattan_distance1(lat1, lon1, lat2, lon2):
  return abs(lat1-lat2) abs(lon1-lon2)

closest 函数修改为:    
def closest_manhattan_distance1(lat,lon,trkpts):
  d = 100000.0
  best = -1
  r = trkpts.index
  for i in r:
    lati = trkpts.ix[i,'Lat']
    loni = trkpts.ix[i,'Lon']
    md = manhattan_distance1(lat, lon, lati, loni)
    if d > md
      best = i
      d = md
  return best
如果将 Manhattan_distance 函数体换进来,速度还可以快些:    
def closest_manhattan_distance2(lat,lon,trkpts):
  d = 100000.0
  best = -1
  r = trkpts.index
  for i in r:
    lati = trkpts.ix[i,'Lat']
    loni = trkpts.ix[i,'Lon']
    md = abs(lat-lati) abs(lon-loni)
    if d > md
      best = i
      d = md
  return best
在计算的最短距离点上,用这个函数与用 John's 的函数效果相同。我希望我的直觉是对的。越简单就越快。现在这个程序用了 2 分 37 秒。提速了 18%。 很好,但还不够激动人心。
我决定正确使用 Python。这意味着要利用 pandas 支持的数组运算。这些数组运算操作源于 numpy 包。通过调用这些数组操作,代码实现更简练:    
def closest(lat,lon,trkpts):
  cl = numpy.abs(trkpts.Lat - lat) numpy.abs(trkpts.Lon - lon)
  return cl.idxmin()
该函数与之前函数的返回结果相同。在我的笔记本上运行时间花费了 0.5 秒。整整快了 300 倍! 300 倍,,也即30,000 %。不可思议。 提速的原因是 numpy 数组操作运算用 C 实现。因此, 我们将最好的两面结合起来了: 我们得到 C 的速度和 Python 的简洁性。
教训很明确:别用 C 的方式写 Python 代码。用 numpy 数组运算,不要用数组遍历。对我来说,这是思维上的转变。
Update on July 2, 2015。文章讨论在Hacker News。一些评论没有注意到(missed )我用到了 pandas 数据帧的情况。主要是它在数据分析中很常用。如果我只是要快速的查询最短距离点,且我时间充分,我可以使用 C 或 C 编写四叉树(实现)。
Second update on July 2, 2015。有个评论提到 numba 也能对代码提速。我就试了一下。
这是我的做法,与你的情况不一定相同。 首先,要说明的是,不同的 python 安装版,实验的结果不一定相同。我的实验环境是 windows 系统上安装 Anaconda,同时也安装了一些扩展包。可能这些包和 numba 存在干扰。.
首先,输入下面的安装命令,安装 numba:    
$ conda install numba

这是我命令行界面上的反馈:

之后我发现,numba 在 anaconda 安装套件中已存在。 也可能安装指令有变更也说不定。
推荐的 numba 用法:    
@jit
def closest_func(lat,lon,trkpts,func):
  d = 100000.0
  best = -1
  r = trkpts.index
  for i in r:
    lati = trkpts.ix[i,'Lat']
    loni = trkpts.ix[i,'Lon']
    md = abs(lat - lati) abs(lon - loni)
    if d > md:
      #print d, dlat, dlon, lati, loni
      best = i
      d = md
  return best

我没有发现运行时间提高。我也尝试了更积极的编译参数设置:    
@jit(nopython=True)
def closest_func(lat,lon,trkpts,func):
  d = 100000.0
  best = -1
  r = trkpts.index
  for i in r:
    lati = trkpts.ix[i,'Lat']
    loni = trkpts.ix[i,'Lon']
    md = abs(lat - lati) abs(lon - loni)
    if d > md:
      #print d, dlat, dlon, lati, loni
      best = i
      d = md
  return best
这次运行代码时,出现一个错误:

看来,pandas 比 numba 处理代码更智能。
当然,我也能花时间修改数据结构,使 numba 能正确编译(compile)。可是,我为什么要这么干呢? 用 numpy 写的代码运行的足够快了。反正,我一直在用 numpy 和 pandas 。为什么不继续用呢?
也有建议我用pypy。这当然有意义,不过…我用的是托管服务器上的 Jupyter notebooks(注,在线浏览器的 python 交互式开发环境)。我用的是它提供的 python 内核,也即,官方的(regular)Python 2.7.x 内核。并没有提供 Pypy 选择。
也有建议用 Cython。好吧,如果我回头要编译代码 ,那我干脆直接用 C 和 C 就好了。我用 python,是因为,它提供了基于 notebooks(注:网页版在线开发环境)的交互式特性,可以快速原型实现。这却不是 Cython 的设计目标。

转载于:https://www.cnblogs.com/amengduo/p/9586322.html

http://www.cda.cn/view/25735.html相关推荐

  1. 在大数据时代,我们需要数据售货员

    在大数据时代,我们需要数据售货员 一直以来,IT产业被奉为高新技术产业,尽管业内经常有各种调侃的声音,但IT业在一般人的印象中还是与科技.潮流等字眼相关.随着全社会信息需求的多样化.消费化,以及青年一 ...

  2. SAS数据挖掘实战篇【六】

    SAS数据挖掘实战篇[六] 6.3  决策树 决策树主要用来描述将数据划分为不同组的规则.第一条规则首先将整个数据集划分为不同大小的 子集,然后将另外的规则应用在子数据集中,数据集不同相应的规则也不同 ...

  3. 企业大数据运用实战案例分享

    一.企业大数据如何起步:从小数据到大数据 目前国内外关于大数据的谈论很多,大多是谈运营级别的,或者说从服务端.服务方提得较多一些.笔者要跟大家交流的问题是作为各类企业尤其是客户方的企业来说,大数据跟他 ...

  4. 【观点见解】解读大数据的5个误区

    [观点见解]解读大数据的5个误区 大数据并不会给你带来大麻烦,事实上,大数据能够帮助你尽量减少业务问题,还能帮助你作出战略性决策.但如果不搞清楚对大数据的一些误区,也可能会给你带来不必要的麻烦.下面就 ...

  5. 大数据时代 树大数据意识

    大数据时代 树大数据意识 一,大数据及其特点 1.什么是大数据? 美国首屈一指的咨询公司麦肯锡给大数据的定义是:大小超出常规的数据库工具获取.存储.管理和分析能力的数据集.全球最大的电子商务公司亚马逊 ...

  6. 内容分析在用户反馈分析中的应用

    内容分析在用户反馈分析中的应用 1:淘宝的用户反馈 入口 PART1 理论基础:内容分析法简述 内容分析,是指利用明晰的编码规则,将大量文本信息转化为定量数据,并 归于若干类别以分析信息特征的方法). ...

  7. 小白学数据分析--回归分析在游戏人气分析的应用探索

    小白学数据分析--回归分析在游戏人气分析的应用探索 昨天简单说了一下相关分析在充值购买失衡方面的应用,今天就接着昨天的话题,说一下回归分析(Regression  Analysis),回归分析是研究一 ...

  8. SPSS单一样本的T检验

    SPSS单一样本的T检验 如果已知总体均数,进行样本均数与总体均数之间的差异显著性检验属于单一样本的T检验.在SPSS中,单一样本的T检验由"One-Sample T Test"过 ...

  9. excel怎么设置密码保护?Excel文件添加密码保护教程

    excel怎么设置密码保护?Excel文件添加密码保护教程 众所周知,Excel具有强大的数据处理和数据分析能力,广泛应用于加工学统计及金融统计中.特别是金融统计需要较高的安全性,那么就一定要为Exc ...

最新文章

  1. 高性能和可扩展的React-Redux
  2. Django中配置自定义日志系统
  3. 也说c#获取windows特殊路径
  4. Java反射机制API
  5. 利用Crontab为Linux定时备份Mysql数据库
  6. 震惊 | 某公司实习生跑路,竟为了学习偷盗面试题
  7. Hadoop CentOS 7 安装配置
  8. 计算机病毒与恶意软件
  9. 深度解析TCP/IP---网络原理的重重之重
  10. iPhone7 plus分辨率行不行
  11. 关于Android studio Translation插件提示“更新 TKK 失败,请检查网络连接”问题
  12. 做视频自媒体必备的工具,手机电脑端都有哦
  13. 数据仓库工程师、大数据开发工程师、BI工程师、ETL工程师之间有什么区别?
  14. UEStudio快捷键
  15. ikbc键盘组合功能键
  16. 使用易语言实现远程CALL调用
  17. 服务器定时执行js脚本
  18. 人工智能的创业方向到底怎么选?
  19. 微信小程序毕业设计 基于微信化妆品商城小程序系统开题报告
  20. 边缘检测系列5:【CED】添加了反向细化路径的 HED 模型

热门文章

  1. 【边缘检测】RCF: Richer Convolutional Features for Edge Detection
  2. 参考文献_参考文献:
  3. ai人工智能收入_人工智能促进收入增长:使用ML推动更有价值的定价
  4. 一场虚拟的鄂尔多斯婚礼 (图)
  5. Deep Belief Networks
  6. C++11 Lambda函数(匿名函数)
  7. python ssh登陆模块_使用python的Paramiko模块登陆SSH
  8. 启动之后自己关闭_电脑一开都是广告,请问怎么永久关闭?
  9. html json解析插件,jQuery插件jsonview展示json数据
  10. python图片隐写_Lsb图片隐写