作者归档:mzh

Python如何查找Follow关系

Twitter中Follower和Followee,现需要找到互相关注的两个人(不关心顺序) 例如:现有列表

 l = [(1, 2), (2, 3), (3, 2), (3, 4), (4, 1),
(4, 3), (4, 3)]

可以通过下列函数生成

def gen_pairs():
return (random.randint(0, 30), random.randint(0, 30))
l = [gen_pairs() for x in xrange(20)]

解法一:

import collections
[x for x, y in collections.Counter([tuple(sorted(x)) for x in l]).iteritems() if y > 1]
  1. [tuple(sorted(x)) for x in l] 首先是将列表的内容按小到大重新排列
  2. 通过计数器collections.Counter,来统计重复的数量
  3. if y > 1 将大于一个的放入结果集中

最后统计用时best of 3: 38.9 µs per loop 老湿,还能给力点吗? 解法二:
[Stackover上的解答](http://stackoverflow.com/questions/22161370/algorithm-to-find-
follow-relationship-like-twitter/22161585#22161585 “Stackover上的解答” )

[x for x in set_l if x[::-1] in set(l)]

快了6倍……答主说到这个算法最快也就是O(n)了,因为必须遍历所有项有木有啊!

2013年终总结

这几天手机上的待办事项里一直提醒着要做总结了,去年的年终总结迫于压力删除了,找都找不回来啊……所以以后的总结就隐去隐私部分吧:)不过,大概记得的3个都实现了,充分说明这玩意还是挺神的,冥冥之中会推动自己实现它们。
2013年,其实还算过得比较充实的,消化了不少技术类书籍:

  • Python编程实践
  • 程序语言的奥妙 : 算法解读
  • SQL反模式 : SQL反模式
  • 黑客与画家 : 硅谷创业之父Paul Graham文集
  • MySQL性能调优与架构设计
  • 简约之美 : 软件设计之道
  • Python学习手册
  • 深入浅出 Python
  • 代码整洁之道
  • Python编程
  • CouchDB指南
  • MongoDB指南

也参加了不少的技术会议,但是总感觉国内的企业没几家是在耐心积攒和发展技术的,全都是一股脑地用最新技术忽悠一阵……好了,咱没有文学青年的细腻,只好继续用问答式的总结模板了。

  1. 今年你所完成的最重要的事情是什么?
    
* 成功从职场菜鸟转化成普通员工,顺便喂饱自己了,职业上发展还算顺利
  1. 今年你所学到的最有用的是什么?
    
* 各种Python技术点,NoSQL入门
  1. 满分10分,你在这一年对自己的满意度有几分?
    
* 总评:6分 及格
  1. 你明年想要实现什么,要不要来个前所未有最棒的一年?
    
* **把《Data Structures and Algorithms Using Python》翻译完**
* 能换到Douban, Mozilla, Opera,Redhat其中之一
* dumpjs能上线,赚回租费
* 微健身,不求肌肉只求少点感冒
* 至少旅游一次
  1. 如果现在是明年的12月31​日,你最想在你的生活中见到什么?
    
* 手上有《**Data Structures and Algorithms Using Python》的译本**

《程序语言的奥妙》之Python实现–Part1

  • 程序就像食谱,严格跟着食谱做饭,味道绝对不会差到哪里去,但是可能就不太好吃。
  • 算法对于程序员,就像棋谱对于棋手,可能一时半回没啥用,但最终认得棋谱多的棋手始终会获胜的
  • 链表的实现就像出门买杂货,逛完肉店买肉,然后再到鱼店买鱼,店之间并没有联系,但使之串起来的是自己的购物单,这张单子就是链表

还有很多对于计算机概念的有趣解释,大家就自己看吧 🙂

进入正题

前面就介绍下这本书,接下来是里面各种经典算法的Python实现,问题和算法神马的大家看书就好了~我就不摘抄了。 有错欢迎指正。

第47节:辗转相除法

或称欧几里得求最大公约数算法

#!/usr/bin/env python
# encoding: utf-8
def Euclid(x, y):
if x < y:
tmp = x
x = y
y = tmp
while y != 0:
rod = x % y
x = y
y = rod
return x
if __name__ == '__main__':
print Euclid(126, 90) # should be 18

第50节:桶排序

#!/usr/bin/env python
# encoding: utf-8
def bucket_sort(lis):
max_item = max(lis)
bucket = [-1 for x in xrange(max_item+1)]
for item in lis:
if item < 0:
raise ValueError("Can't handle %d" % item)
bucket[int(item)] = item
return filter(lambda x: x != -1, bucket)
if __name__ == '__main__':
print bucket_sort([8,2,1,5,9,7]) # should be [1,2,5,7,8,9]

第51节:基位排序—-桶排序的升级版

#!/usr/bin/env python
# encoding: utf-8
from copy import deepcopy
def bit_sort(lis):
bucket = [[] for x in xrange(len(lis))]
k = len(str(max(lis))) # sort time
array = [deepcopy(bucket) for x in xrange(k)]
for time in xrange(k):
if time == 0:
for l in lis:
array[0][int(str(l)[-1])].append(l)
else:
for b in array[time-1]:
for item in b:
try:
array[time][int(str(item)[-1-time])].append(item)
except IndexError:
array[time][0].append(item)
return array
if __name__ == '__main__':
for line in bit_sort([123, 602, 82, 777, 57, 510, 396, 196, 843, 138]):
print line
print "The Last line should be:[[57, 82], [123, 138, 196], [], [396], [], [510], [602], [777], [843], []]"

中国县及县以上地区数据结构【Python】

郭嘉统计局虽然经常更新地区数据,但是其数据结构糟糕透顶,plain
HTML有没有!都不提供SQL或者是XML数据类型! 都还得写个解析器来加载这个结构,用LXML解析的过程我就不写了
去除各种table之后的数据库

110000 北京市 110100 市辖区 110101 东城区 110102 西城区 110105 朝阳区 110106 丰台区 110107
石景山区 110108 海淀区

转换以后:

省:北京
   ├─ 市辖区
   │  ├─ 东城区
   │  ├─ 西城区
   │  ├─ 朝阳区
   │  ├─ 石景山区
   │  ├─ 海淀区
   │  ╰─ 平谷区
   ╰─ 县
      ├─ 密云县
      ╰─ 延庆县

规律就是邮政编码!用了groupby和defaultdict这些基本的Python东西 下面是程序啦,用法是直接打省份的名称即可。
当然,函数已经是单独实现的,所以在其他地方用也行啦~


#!/usr/bin/env python
# encoding: utf-8
from itertools import groupby
from utils import ScaleTree
def make_city_tree(path):
"""
 make a tree of province, city, county of China

 :path: path to database
 :returns: tree

 """
def strip_zipcode(item):
"""
 Strip all zipcode from stats.gov.cn
 :returns: city_name
 """
return item[7:].decode('utf8').strip()
with file(path, 'r') as db:
tree = ScaleTree()
provinces = groupby(db, key=lambda x: x[:2])
for pid, province_data in provinces:
province_data = list(province_data)
province_name, cities = strip_zipcode(province_data[0]), province_data[1:]
for cid, city_data in groupby(cities, key=lambda x: x[:4]):
city_data = list(city_data)
city_name, counties = strip_zipcode(city_data[0]), city_data[1:]
tree[province_name][city_name] = map(strip_zipcode, counties)
return tree
if __name__ == '__main__':
tree = make_city_tree('db.txt')
pro = unicode(raw_input('省:'), 'utf8')
for x in tree.keys():
if pro in x:
cities = tree.get(x)
for t, city in enumerate(cities):
if t+1 != len(cities):
st = u"├"
else:
st = u'╰'
print u"\u2004\u2004\u2004%s\u2004%s" % (st, city)
for d, county in enumerate(tree.get(x).get(city)):
if d+1 != len(tree.get(x).get(city)):
st = u"├"
else:
st = u'╰'
if t+1 != len(cities):
ct = u"│"
else:
ct = u"\u2004"
print u"\u2004\u2004\u2004%s\u2004\u2004%s\u2004%s" % (ct, st, county)

最近一些面试题(Python)

最近换工作,面了几家公司,超大,大,中,小都有,不过就不提名字了。 唯一的感触就是自己实在是太浪费四年的时间在游戏上了,要是腾出时间搞算法那是极好啊。
不过我总觉得知识的欠缺是可以通过学习来弥补的,同时,记录也是学习的一部分,现在我就写写我还记得的几道面试题。

骑士巡游问题

一道简单的BFS(广度优先)算法题

在一个国际象棋棋盘上 (NN),有一个棋子"马(Knight)",处在任意位置(x, y);
马的走法是日字型,即其可以在一个方向上前进或后退两格,在另一方向上前 进或 后退一格。 请编程找出马如何从位置(x, y)走到棋盘右下角(N,
N)的位置的步骤。 例如:假设棋盘大小为3
3,马处在(1,2)位置,马只需要走一步, 即 (1,2)-> (3,3)即可到达目的地。

具体代码我已经push到github上了,链接在此
对于从来没有研究过算法的我来说,整个题目的难处在理解队列这个概念上。
广度优先的队列之奇妙的地方在于,每一层的尝试,都先放入队列中,紧接着,挨个判断队列中的元素是否达成了目标。对,就这么简单。

Fibonacci数列

好吧~两家公司都考这斐波那契……

用Python生成指定长度的斐波那契数列

考递归:

def fib_recursion(n):
if 0< = n < 2:
return 1
else:
return fib_recursion(n-1)+fib_recursion(n-2)
print fib_recursion(99) # 调用即可

不错吧~完美地使用了递归,当然,如果能用字典存储,这样更完美了对吧? 错! 其实考的是iterable的使用,Python CookBook
19.3里那极为精妙的解法才可以称得上答案:

def fib():
x, y = 0,1
while True:
yield x
x, y = y,x+y
if __name__ == '__main__':
import itertools
print list(itertools.islice(fib(), 10))

LRU缓存

现场编程题,1小时之内写出可用的LRU cache util

其实当场没有写出来,主要是因为还不清楚list的pop()中如果有数字的话,就是O(n)的复杂度,我当时的水平最多写得出[这个源里的程度](https://github.com/mengzhuo
/django-lru-cache)。用的是dict的popitem,而且是面试官说在生产系统中也使用这样的方法。 后来,仔细看了Python
Cookbook(知道是好书了吧),发现collections的deque神器,不过正反向双list也是个不错的ADT选择,而且这些连面试官都不知道。
具体的应用以后写读书笔记时会和大家分享下的。