WEB开发网
开发学院软件开发Python Pyrex 扩展并加速 Python 应用程序 阅读

Pyrex 扩展并加速 Python 应用程序

 2007-03-29 12:21:49 来源:WEB开发网   
核心提示: 剖析有些东西似乎不对,速度提高几个百分比和 Pyrex 主页(以及很多 Pyrex 用户)那样提高 40 倍有很大的差距,Pyrex 扩展并加速 Python 应用程序(7),现在应该来看一下这个 Python _mint() 函数中 哪些 地方真正消耗了时间,有一个 quick 脚本(此

剖析

有些东西似乎不对。速度提高几个百分比和 Pyrex 主页(以及很多 Pyrex 用户)那样提高 40 倍有很大的差距。现在应该来看一下这个 Python _mint() 函数中 哪些 地方真正消耗了时间。有一个 quick 脚本(此处没有给出)可以分解复杂操作 sha(challenge+hex(counter)[2:]).hexdigest():

清单 8. hashcash 的 mint 函数的时间消耗1000000 empty loops:   0.559
------------------------------
1000000 sha()s:     2.332
1000000 hex()[2:]s:   3.151
  just hex()s:     <2.471>
1000000 concatenations: 0.855
1000000 hexdigest()s:  3.742
------------------------------
Total:         10.079

显然,我并不能将这个循环从 _mint() 函数中删除。虽然 Pyrex 改进后的 for 循环可能有一点加速,但是整个函数主要是一个循环。我也不能删除对 sha() 的调用,除非要使用 Pyrex 重新实现 SHA-1(即使我要这样做,也没有自信自己可以比 Python 标准的 sha 模块的作者做得更好)。而且,如果我希望得到一个 sha.SHA 对象的 hash 值,就只能调用 .hexdigest() 或 .digest();前者的速度更快。

现在真正要解决的是 hex() 对 counter 变量的转换,以及结果中时间片的消耗情况。我可能需要使用 Pyrex/C 的字符串连接操作,而不是 Python 的字符串对象。然而,我见过的惟一一种避免 hex() 转换的方法是手工在嵌套循环之外构建一个后缀。虽然这样做可以避免 int 到 char 类型的转换,但是需要生成更多代码:

清单 9. 完全 Pyrex 优化过的 mint 函数cdef _mint(char *challenge, int bits):
  cdef int hex_digits, i0, i1, i2, i3, i4, i5
  cdef char *ab, *digest, *trial, *suffix
  suffix = '******'
  ab = alphabet
  hex_digits = int(ceil(bits/4.))
  hash = sha
  for i0 from 0 <= i0 < 55:
    suffix[0] = ab[i0]
    for i1 from 0 <= i1 < 55:
      suffix[1] = ab[i1]
      for i2 from 0 <= i2 < 55:
        suffix[2] = ab[i2]
        for i3 from 0 <= i3 < 55:
          suffix[3] = ab[i3]
          for i4 from 0 <= i4 < 55:
            suffix[4] = ab[i4]
            for i5 from 0 <= i5 < 55:
              suffix[5] = ab[i5]
              py_digest = hash(challenge+suffix).hexdigest()
              digest = py_digest
              for i from 0 <= i < hex_digits:
                if digest[i] != c'0': break
              else:
                return suffix

上一页  2 3 4 5 6 7 8 9  下一页

Tags:Pyrex 扩展 加速

编辑录入:爽爽 [复制链接] [打 印]
赞助商链接