21 08年6月

转贴一个Python HTMLParser的使用例子

关键字:,

原文
http://crquan.blogbus.com/logs/8269701.html

#!/usr/bin/env python
 
import sys
import urllib
import HTMLParser
 
class CustomParser(HTMLParser.HTMLParser):
    
selected = ('table', 'h1', 'font', 'ul', 'li', 'tr', 'td', 'a')
    
    
def reset(self):
        
HTMLParser.HTMLParser.reset(self)
        
self._level_stack = []
    
def handle_starttag(self, tag, attrs):
        
if tag in CustomParser.selected:
            
self._level_stack.append(tag)
    
def handle_endtag(self, tag):
        
if self._level_stack \
        
and tag in CustomParser.selected \
        
and tag == self._level_stack[-1]:
            
self._level_stack.pop()
    
def handle_data(self, data):
        
if "/".join(self._level_stack) in (
            
'table/tr/td',
            
'table/tr/td/h1/font',
            
'table/tr/td/ul/li'):
            
print self._level_stack, data
        
if len(sys.argv) > 1:
    
params = urllib.urlencode({'ip': sys.argv[1], 'action': 2})
else:
    
params = None
 
content = unicode(urllib.urlopen('http://www.ip138.com/ips8.asp',params).read(), 'GB2312')
 
parser = CustomParser()
parser.feed(content)
parser.close()

贝贝爸 发表在 技术文章 | 等您写评论

24 08年4月

python读有文件结束符的txt文本文件

关键字:,

一直用python读文件都是文本文件。用的方法是:

lines=open('ft.txt')

但是前两天读一个几百兆的大文件的时候,遇到了奇怪的问题,觉得是内容没有读完。定位最后读到的行,用emeditor打开,发现有一个怪字符“”。编码是“\x001a”,一查,原来是文件结束符号。
一直郁闷,奇怪为啥文本文件里面有文件结束符,试了好多办法,都不行,最后经limodou指点,原来这种情况要当成二进制文件来读。

lines=open('ft.txt','rb')

文件内容如下:

abcdefg

两种不同情况的结果如下:

>>> f=open('ft.txt')
>>>
f.read()
'abc'
>>>
f=open('ft.txt','rb')
>>>
f.read()
'abc\x1adefg'

贝贝爸 发表在 原创技术文章 | 等您写评论

14 08年4月

python非贪婪、多行匹配正则表达式例子

关键字:,

一些regular的tips:

1 非贪婪flag

>>> re.findall(r"a(\d+?)", "a23b")
        
['2']
>>>
re.findall(r"a(\d+)", "a23b")
        
['23']

注意比较这种情况:

>>> re.findall(r"a(\d+)b", "a23b")
        
['23']
>>>
re.findall(r"a(\d+?)b", "a23b")
        
['23']

2 如果你要多行匹配,那么加上re.S和re.M标志
re.S:.将会匹配换行符,默认.不会匹配换行符

>>> re.findall(r"a(\d+)b.+a(\d+)b", "a23b\na34b")
        
[]
>>>
re.findall(r"a(\d+)b.+a(\d+)b", "a23b\na34b", re.S)
        
[('23', '34')]
>>>

re.M:^$标志将会匹配每一行,默认^和$只会匹配第一行

>>> re.findall(r"^a(\d+)b", "a23b\na34b")
        
['23']
>>>
re.findall(r"^a(\d+)b", "a23b\na34b", re.M)
        
['23', '34']

但是,如果没有^标志,

>>> re.findall(r"a(\d+)b", "a23b\na23b")
        
['23', '23']

可见,是无需re.M

贝贝爸 发表在 技术文章 | 等您写评论

9 08年4月

python正则表达式学习

关键字:,

出处
python 中的re 模块

正则表达式

就个人而言,主要用它来做一些复杂字符串分析,提取想要的信息
学习原则:够用就行,需要的时候在深入

现总结如下:

正则表达式中特殊的符号:

“.” 表任意字符
“^ ” 表string起始
“$” 表string 结束
“*” “+” “?” 跟在字符后面表示,0个——多个, 1个——多个, 0个或者1个
*?, +?, ?? 符合条件的情况下,匹配的尽可能少//限制*,+,?匹配的贪婪性
{m} 匹配此前的字符,重复m次
{m,n} m到n次,m,n可以省略

举个例子 ‘a.*b’ 表示a开始,b结束的任意字符串
a{5} 匹配连续5个a

[] 表一系列字符 [abcd] 表a,b,c,d [^a] 表示非a
| A|B 表示A或者B , AB为任意的正则表达式 另外|是非贪婪的如果A匹配,则不找B
(…) 这个括号的作用要结合实例才能理解, 用于提取信息

\d [0-9]
\D 非 \d
\s 表示空字符
\S 非空字符
\w [a-zA-Z0-9_]
\W 非 \w

一:re的几个函数

1: compile(pattern, [flags])
根据正则表达式字符串 pattern 和可选的flags 生成正则表达式 对象

生成正则表达式 对象(见二)

其中flags有下面的定义:
I 表示大小写忽略
L 使一些特殊字符集,依赖于当前环境
M 多行模式 使 ^ $ 匹配除了string开始结束外,还匹配一行的开始和结束
S “.“ 匹配包括‘\n’在内的任意字符,否则 . 不包括‘\n’
U Make \w, \W, \b, \B, \d, \D, \s and \S dependent on the Unicode character properties database
X 这个主要是表示,为了写正则表达式,更可毒,会忽略一些空格和#后面的注释

其中S比较常用,
应用形式如下
import re
re.compile(……,re.S)

2: match(pattern,string,[,flags])
让string匹配,pattern,后面分flag同compile的参数一样
返回MatchObject 对象(见三)

3: split( pattern, string[, maxsplit = 0])
用pattern 把string 分开
>>> re.split(’\W+’, ‘Words, words, words.’)
[’Words’, ‘words’, ‘words’, ”]
括号‘()’在pattern内有特殊作用,请查手册

4:findall( pattern, string[, flags])
比较常用,
从string内查找不重叠的符合pattern的表达式,然后返回list列表

5:sub( pattern, repl, string[, count])
repl可以时候字符串,也可以式函数
当repl是字符串的时候,
就是把string 内符合pattern的子串,用repl替换了

当repl是函数的时候,对每一个在string内的,不重叠的,匹配pattern
的子串,调用repl(substring),然后用返回值替换substring

>>> re.sub(r’def\s+([a-zA-Z_][a-zA-Z_0-9]*)\s*\(\s*\):’,
… r’static PyObject*\npy_\1(void)\n{’,
… ‘def myfunc():’)
’static PyObject*\npy_myfunc(void)\n{’

>>> def dashrepl(matchobj):
… if matchobj.group(0) == ‘-’: return ‘ ‘
… else: return ‘-’
>>> re.sub(’-{1,2}’, dashrepl, ‘pro—-gram-files’)
‘pro–gram files’

二:正则表达式对象 (Regular Expression Objects )

产生方式:通过 re.compile(pattern,[flags])回

match( string[, pos[, endpos]]) ;返回string[pos,endpos]匹配
pattern的MatchObject(见三)

split( string[, maxsplit = 0])
findall( string[, pos[, endpos]])
sub( repl, string[, count = 0])
这几个函数和re模块内的相同,只不过是调用形式有点差别

re.几个函数和 正则表达式对象的几个函数,功能相同,但同一程序如果
多次用的这些函数功能,正则表达式对象的几个函数效率高些

三:matchobject

通过 re.match(……) 和 re.compile(……).match返回

该对象有如下方法和属性:

方法:
group( [group1, …])
groups( [default])
groupdict( [default])
start( [group])
end( [group])

说明这几个函数的最好方法,就是举个例子

matchObj = re.compile(r”(?P\d+)\.(\d*)”)
m = matchObj.match(’3.14sss’)
#m = re.match(r”(?P\d+)\.(\d*)”, ‘3.14sss’)

print m.group()
print m.group(0)
print m.group(1)
print m.group(2)
print m.group(1,2)

print m.group(0,1,2)
print m.groups()
print m.groupdict()

print m.start(2)
print m.string

输出如下:
3.14
3.14
3
14
(’3′, ‘14′)
(’3.14′, ‘3′, ‘14′)
(’3′, ‘14′)
{’int’: ‘3′}
2
3.14sss

所以group() 和group(0)返回,匹配的整个表达式的字符串
另外group(i) 就是正则表达式中用第i个“()” 括起来的匹配内容
(’3.14′, ‘3′, ‘14′)最能说明问题了。

更进一步的学习,请看手册

贝贝爸 发表在 技术文章 | 等您写评论

8 08年4月

python中关于文件路径的简单操作

关键字:

出处
python中关于文件路径的简单操作

几个主要的函数:

1: os.listdir(path) //path为目录

功能相当于在path目录下执行dir命令,返回为list类型
举例:
print os.listdir(’..’)
输出:
[a,b,c,d]

2: os.path.walk(path,visit,arg)

path :是将要遍历的目录
visit :是一个函数指针,函数圆形为:
callback(arg,dir,fileList)
其中arg为为传给walk的arg , dir是path下的一个目录,fileList为dir下的文件和目录组成的list
arg:传给visit用的,对walk没有什么作用

举例:
def callback(arg,directory, files):
print directory,
print files,
print arg
print ‘——————–’

os.path.walk(’.',callback, ‘123456′)

输出:
. [’path0704.py’, ‘temp’, ‘\xc2\xb7\xbe\xb6\xcf\xe0\xb9\xd8\xd1\xa7\xcf\xb0.txt’] 123456
——————–
.\temp [’temp.h’, ‘temp1′] 123456
——————–
.\temp\temp1 [’abc.bmp’] 123456

如果想找到某个目录下所有文件,只需要在callback里面,在fileList中找出文件,即可

除此之外,还有一个函数可以用那就是os.walk,看10

3:os.path.split(path)
path 为一个路径,

输出,把path分成两部分,具体看实例:
print os.path.split(”abc/de.txt”)
(’abc’, ‘de.txt’)
os.path.split(”abc”)
(”, ‘abc’)
print os.path.split(”de/abc/de”)
(’de/abc’, ‘de’)

4: os.path.splitext(filename)
把文件名分成文件名称和扩展名
os.path.splitext(abc/abcd.txt)
(’abc/abcd’, ‘.txt’)

5: os.path.dirname(path)
把目录名提出来
print os.path.dirname(”abc”)
#输出为空
print os.path.dirname(’abc\def’)
abc

6: os.path.basename(filename)
取得主文件名
print os.path.basename(’abc’)
abc
print os.path.basename(’abc.txt’)
abc
print os.path.basename(’bcd/abc’)
abc #这个需要注意不包括目录名称
print os.path.basename(’.')
.

7:os.mkdir(path, [mode])
path为目录名: 这里有个要求,只能创建一级目录
比如path为 abc/def 则当前目录下必须存在abc 否则失败

8: os.makedirs(path [,mode])
可以创建多级目录

9:os.remove(path)删除一个文件,一定是一个文件
os.removedirs(path) 删除一个目录下所有东西
os.rmdir(path) 删除一个目录,而且一定要空,否则os.errer

10:os.walk(path)
遍历path,返回一个对象,他的每个部分都是一个三元组
(’目录x’,[目录x下的目录list],目录x下面的文件)

举例:
a = os.walk(’.')
for i in a:
print i
输出:
(’.', [’abc’, ‘temp’], [’path0704.py’, ‘\xc2\xb7\xbe\xb6\xcf\xe0\xb9\xd8\xd1\xa7\xcf\xb0.txt’])
(’.\\abc’, [], [’\xd0\xc2\xbd\xa8 BMP \xcd\xbc\xcf\xf1.bmp’])
(’.\\temp’, [’temp1′], [’temp.h’])
(’.\\temp\\temp1′, [], [’abc.bmp’])

11:shutil.copy(src,dst)
把文件src内容拷贝到文件dst中。,目标区域必须可以写,如果dst存在,则dst被覆盖

上面的函数基本够用
其它文件移动操作还请看:shutil模块:High-level file operations

贝贝爸 发表在 技术文章 | 等您写评论

11 07年6月

python登录并校验是否成功

关键字:

为了监控网站运行是否正常,写了一个脚本来检查网站运行的情况。
主要是自动登录并且校验登陆后的内容来判断网站web服务和数据库服务是否正常。
代码如下:

#!/usr/bin/env python
# -*- coding: gbk -*-
import urllib
import urllib2
import ClientCookie
import re
import string
import time
import socket
timeout=10
server="www.juyimeng.com"
loginurl="http://"+server+"/login.php"
v_account=[
{
"name":"user1","pass":"pass1","utype":"1","vkey":"用户1"},
{
"name":"user2","pass":"pass2","utype":"2","vkey":"用户2"}
]
def fes_write(s):
    
'''
    控制输出信息的显示
    
'''
    
print s
def get_response(x):
    
'''
    登录,取得登陆后的页面html代码,用来判断结果
    
'''
    
fes_write("login for "+ x["name"])
    
eform = {'username':x["name"], 'password':x["pass"], 'usertype':x["utype"]}
    
qstring = urllib.urlencode( eform )
    
#print qstring
    
try:
        
request = urllib2.Request( loginurl , qstring )
        
response = ClientCookie.urlopen( request )
        
return string.split( response.read(),"\n")
    
except Exception, e:
        
fes_write(e)
        
return "error"
def verify_info(k,l):
    
'''
    校验信息是否正确
    
'''
    
for line in l:
        
if k.match(line):
            
return True
            
break
    
return False
def verify_all():
    
'''
    主程序,进行校验
    
'''
    
if timeout!=0:
        
socket.setdefaulttimeout(timeout )
    
fes_write("socket time out: " + str(socket.getdefaulttimeout()))
    
success_num=len(v_account)
    
for x in v_account:
        
vkey=re.compile('.*'+x["vkey"]+'.*')
        
if verify_info(vkey,get_response(x))==True:
            
success_num=success_num-1
            
fes_write(x["name"]+ " login success!")
        
else:
            
fes_write("error when " + x["name"]+ "login!")
    
if success_num==0:
        
fes_write("all things runs well!")
    
else:
        
e_notify()
        
fes_write("some thing is wrong!")
        
def e_notify():
    
'''
    出错之后的notify操作
    
'''
    
pass
if __name__ == '__main__':
    
verify_all()

v_account定义了多个账户,因为用户可能不同,后台机制不一样,所以用多个用户来登录
request = urllib2.Request( loginurl , qstring ) 用的是post的方法,也可以用get的方法。
ClientCookie,一个python的扩展包,安装请参考这里
2个v_account里的vkey用来和登陆后的页面上的信息来验证是否正常登录的
socket.setdefaulttimeout用来设置建立socket连接的超时设置,原来没有设置,程序会一直等待回应(如果服务器端做了最长运行时间会好点),设置了10秒,如果一个登录程序10秒还没有成功,基本上就失败了。
e_notify:可以自己设置一些notify的方法,比如邮件,短消息等。

贝贝爸 发表在 原创技术文章 | 等您写评论

9 07年6月

简单的python smtp发邮件代码

关键字:

写了一个服务器的监控程序,里面用到邮件提醒功能。python sample code里面没有认证的部分,于是查了文档,google了一下,下了如下的smtp发送邮件的函数,支持smtp验证。代码如下:

#!/usr/bin/env python
# -*- coding: gbk -*-
#导入smtplib和MIMEText
import smtplib
from email.mime.text import MIMEText
#############
#要发给谁,这里发给2个人
mailto_list=["aaa@juyimeng.com","bbb@juyimeng.com"]
#####################
#设置服务器,用户名、口令以及邮箱的后缀
mail_host="smtp.126.com"
mail_user="xxx"
mail_pass="yyy"
mail_postfix="126.com"
######################
def send_mail(to_list,sub,content):
    
'''
    to_list:发给谁
    sub:主题
    content:内容
    send_mail("aaa@126.com","sub","content")
    
'''
    
me=mail_user+"<"+mail_user+"@"+mail_postfix+">"
    
msg = MIMEText(content)
    
msg['Subject'] = sub
    
msg['From'] = me
    
msg['To'] = ";".join(to_list)
    
try:
        
s = smtplib.SMTP()
        
s.connect(mail_host)
        
s.login(mail_user,mail_pass)
        
s.sendmail(me, to_list, msg.as_string())
        
s.close()
        
return True
    
except Exception, e:
        
print str(e)
        
return False
if __name__ == '__main__':
    
if send_mail(mailto_list,"subject","content"):
        
print "发送成功"
    
else:
        
print "发送失败"

有问题请指教

贝贝爸 发表在 原创技术文章 | 1个评论

2 07年6月

python常用的时间方法

关键字:

我们先导入必须用到的一个module
>>> import time
设置一个时间的格式,下面会用到
>>>ISOTIMEFORMAT=’%Y-%m-%d %X’
看一下当前的时间,和其他很多语言相似这是从epoch(1970 年 1 月 1 日 00:00:00)开始到当前的秒数。
>>> time.time()
1180759620.859
上面的看不懂,换个格式来看看
>>> time.localtime()
(2007, 6, 2, 12, 47, 7, 5, 153, 0)
localtime返回tuple格式的时间,有一个和它类似的函数叫gmtime(),2个函数的差别是时区,gmtime()返回的是0时区的值,localtime返回的是当前时区的值。
>>> time.strftime( ISOTIMEFORMAT, time.localtime() )
‘2007-06-02 12:54:29′
用上我们的时间格式定义了,使用strftime对时间做一个转换,如果取现在的时间,time.localtime() 可以不用。

>>> time.strftime( ISOTIMEFORMAT, time.localtime( time.time() ) )
‘2007-06-02 12:54:31′
>>> time.strftime( ISOTIMEFORMAT, time.gmtime( time.time() ) )
‘2007-06-02 04:55:02′
上面展示了gmtime和localtime的区别。
查看时区用
>>> time.timezone
-28800
上面的值是一个秒值,是当前时区和0时区相差的描述,-28800=-8*3600,即为东八区。

帖几个简单的函数

def ISOString2Time( s ):
    
'''
    convert a ISO format time to second
    from:2006-04-12 16:46:40 to:23123123
    把一个时间转化为秒
    
'''
    
return time.strptime( s, ISOTIMEFORMAT )
def Time2ISOString( s ):
    
'''
    convert second to a ISO format time
    from: 23123123 to: 2006-04-12 16:46:40
    把给定的秒转化为定义的格式
    
'''
    
return time.strftime( ISOTIMEFORMAT, time.localtime( float( s ) ) )
def dateplustime( d, t ):
    
'''
    d=2006-04-12 16:46:40
    t=2小时
   return  2006-04-12 18:46:40
   计算一个日期相差多少秒的日期,time2sec是另外一个函数,可以处理,3天,13分钟,10小时等字符串,回头再来写这个,需要结合正则表达式。
    
'''
    
return Time2ISOString( time.mktime( ISOString2Time( d ) )+time2sec( t ) )
def dateMinDate( d1, d2 ):
    
'''
    minus to iso format date,return seconds
    计算2个时间相差多少秒
    
'''
    
d1=ISOString2Time( d1 )
    
d2=ISOString2Time( d2 )
    
return time.mktime( d1 )-time.mktime( d2 )

贝贝爸 发表在 原创技术文章 | 等您写评论

1 07年6月

在linux下安装activepython2.5 setuptools ClientCookie

关键字:, ,

activepython
http://www.activestate.com/products/activepython/
是ActiveState Software的一个python的分发包,带了一些python的扩展.
setuptools
http://cheeseshop.python.org/pypi/setuptools
是一个python的包,它可以简化python包的下载,build,安装升级和卸载
ClientCookie
http://wwwsearch.sourceforge.net/ClientCookie/
是一个python对cookie功能的扩展,从HTTP::Cookies而来。作者说以后不会再发布单独的模块,已经集成到了mechanize里面。

下载上述软件
wget http://downloads.activestate.com/ActivePython/linux/2.5/ActivePython-2.5.1.1-linux-x86.tar.gz
wget http://wwwsearch.sourceforge.net/ClientCookie/src/ClientCookie-1.3.0.tar.gz
wget http://cheeseshop.python.org/packages/2.5/s/setuptools/setuptools-0.6c6-py2.5.egg

先安装ActivePython
tar zxvf ActivePython-2.5.1.1-linux-x86.tar.gz
cd ActivePython-2.5.1.1-linux-x86
./install.sh
输入安装的目录,我输入了/usr/local/python25/
装好后看一下

[jym@jym jym]$ /usr/local/python25/bin/python
ActivePython 2.5.1.1 (ActiveState Software Inc.) based on
Python 2.5.1 (r251:54863, May  1 2007, 17:48:28)
[GCC 2.95.3 20010315 (SuSE)] on linux2
Type "help", "copyright", "credits" or "license" for more information.
%3E%3E%3E%20

本来应该直接安装ClientCookie的,安装过程中要使用setuptools,它应该自动下载,安装的,但是由于ClientCookie用的url不对,用的是
http://cheeseshop.python.org/packages/2.5/s/setuptools/setuptools-0.6a11-py2.5.egg
所以不能自动下载,只好手工下载,安装
安装
setuptools
在setuptools-0.6c6-py2.5.egg所在的目录运行

ln -s  /usr/local/python25/bin/python2.5 python2.5
PATH=.:$PATH 
sh setuptools-0.6c6-py2.5.egg
rm python2.5

安装ClientCookie

tar zxvf ClientCookie-1.3.0.tar.gz
cd ClientCookie-1.3.0
/usr/local/python25/bin/python setup.py build
/usr/local/python25/bin/python setup.py install

至此,activepython2.5+setuptools+ClientCookie在linux的安装已经完成,ClientCookie的简单使用等俺下一篇再说:D
BTW:祝大家6.1快乐!

贝贝爸 发表在 原创技术文章 | 2个评论

22 07年5月

python读书笔记-1

关键字:

特殊符号,星号(*)的作用

* unpacking argument lists
分解开list类型的参数

** unpacking argument dicts
分解开dict类型的参数

iteritems()
retrieved the key and value of dict
上述函数可以得到dict的key和value

python怎么取得系统环境变量的值?
os.environ.get(’path’)

python中导入模块搜索的顺序
1当前目录
2pythonpath
3,path
4install dir

怎么修改python的提示符用
修改sys.ps1,sys.ps2的值

添加搜索模块的目录

sys.path.append

看对象都有什么方法和属性
dir以及dir(__builtin__)

repr
repr函数用来取得对象的规范字符串表示。反引号(也称转换符)可以完成相同的功能。

格式化输出的函数
ljust,rjust,center,zfile

for,while loop 可以和else组合使用

try…except可以后边加上else
else必须在所有的excep后边,当try里面没有异常的时候,执行else的语句,可以避免截获不属于保护代码里面的异常。

确保关闭文件的读文件方法

with open("mf.txt") as f:
    
for l in f:
        
print l

贝贝爸 发表在 原创技术文章 | 等您写评论

美体小铺急救棒 the bodyshop body shop 美体小铺茶树精油 美体小铺接骨木花眼胶 美体小铺VE眼霜
美体小铺急救棒 the bodyshop body shop 美体小铺茶树精油 美体小铺接骨木花眼胶 美体小铺VE眼霜