【Python爬虫】爬取成绩计算绩点

  昨天太忙了,就没写这篇博客,今天补上。

  1.地址分析

   在登陆页面打开开发者工具栏(要启用持续日志),随便输入点登陆,可以看到采用的是POST的方式提交的参数,有两个隐藏参数,并且用户名密码没有加密。记下提交地址http://jwgl.ntu.edu.cn/cjcx/Default.aspx

和两个隐藏参数的值

"__VIEWSTATE":"/wEPDwUJODExMDE5NzY5ZGRgtUdRucUbXsT8g55XmVsTwV6PMw==",
"__VIEWSTATEGENERATOR":"6C0FF253",

   

 还有一个地址是获取验证码的记下地址:http://jwgl.ntu.edu.cn/cjcx/checkImage.aspx

  我用自己的账号登进去,点击全部成绩,可以看到又有一个POST请求,两个参数简单猜一下应该是起始课程号和结束课程号。记下POST的地址:http://jwgl.ntu.edu.cn/cjcx/Data/ScoreAllData.aspx


   2.验证码问题

   请求一次验证码就会得到一个SessionId,请求Default.aspx却没有

   所以自己定义一个带cookie的opener,先用它请求验证码,并把验证码保存到本地,然后人工识别输入后,在向Default.aspx发送请求。

cj=cookielib.CookieJar()
headler=urllib2.HTTPCookieProcessor(cj)
opener=urllib2.build_opener(headler)
yzm=opener.open(url1)
yzmgif=open("yzm.gif","w")
yzmgif.write(yzm.read())
yzmgif.close()
print u"验证码已保存在本文件目录下(yzm.gif),请查看并输入!"
yzmstr=raw_input()
  3.数据分析
    观察请求全部成绩响应的数据,开以看出没门课程是以键值对的形式返回来的,

 那么用一下正则表达式来匹配

restr='"kcmc":"(.*?)","jsxm":"(.*?)","xq":"(.*?)","xs":"(.*?)","xf":"(.*?)","zpcj":"(.*?)","pscj":"(.*?)","qmcj":"(.*?)","kcsx":"(.*?)","cjid":"(.*?)","ksfsm":"(.*?)","pxcj":"(.*?)"}'
pattern=re.compile(restr)
items=re.findall(pattern,scorestr)


  4.绩点计算方法(不一定对)

    

1考核成绩与绩点关系:
  五级记分 绩点  百分记分   绩点
  优秀   4.5   90~100  4.0~5.0
  良好   3.5   80~89   3.0~3.9
  中等   2.5   70~79   2.0~2.9
  及格   1.5   60~69   1.0~1.9
  不及格  0     <60    0
2.学分绩点、平均学分绩点的计算。
  课程学分绩点=课程学分×考核成绩绩点
  平均学分绩点=Σ所修课程学分绩点/Σ所修课程学分


             5.运行结果


     6.完整代码(刚学Python,代码风格神乱并且完全没有做容错处理,大神勿笑)   

#!/usr/bin/env python
# -*- coding:utf-8 -*-
import urllib2
import urllib
import cookielib
import re


def getjd(item):
	if item[5]=="优":
		return 4.5*float(item[4])
	if item[5]=="良":
		return 3.5*float(item[4])
	if item[5]=="中":
		return 2.5*float(item[4])
	if item[5]=="及格":
		return 1.5*float(item[4])
	if item[5]=="不及格":
		return 0.0
	if int(item[5])>=90 and int(item[5])<=100:
		return ((float(item[5])-90)/10+4.0)*float(item[4])
	if int(item[5])>=80 and int(item[5])<=89:
		return ((float(item[5])-80)/10+3.0)*float(item[4])
	if int(item[5])>=70 and int(item[5])<=79:
		return ((float(item[5])-70)/10+2.0)*float(item[4])
	if int(item[5])>=60 and int(item[5])<=69:
		return ((float(item[5])-60)/10+1.0)*float(item[4])
	if int(item[5])<=59:
		return 0.0

cj=cookielib.CookieJar()
headler=urllib2.HTTPCookieProcessor(cj)
opener=urllib2.build_opener(headler)
url="http://jwgl.ntu.edu.cn/cjcx/Default.aspx"		#登录页面
url1="http://jwgl.ntu.edu.cn/cjcx/checkImage.aspx"	#验证码页面
scoreurl="http://jwgl.ntu.edu.cn/cjcx/Data/ScoreAllData.aspx"#获取分数
#输入数据
print u"××××××××××××××××××××南通大学教务系统登陆××××××××××××××××××××"
print u"输入学号!"
xh=raw_input()
print u"输入身份证号!"
sfzh=raw_input()
print u"密码!"
kl=raw_input()
yzm=opener.open(url1)
yzmgif=open("yzm.gif","w")    #保存验证码
yzmgif.write(yzm.read())
yzmgif.close()
print u"验证码已保存在本文件目录下(yzm.gif),请查看并输入!"
yzmstr=raw_input()
#数据保存
jilu=open(xh+".txt","w")
jilu.write("学号:"+xh+"
身份证号:"+sfzh+"
密码:"+kl)
jilu.close()
values={"__VIEWSTATE":"/wEPDwUJODExMDE5NzY5ZGRgtUdRucUbXsT8g55XmVsTwV6PMw==",
	"__VIEWSTATEGENERATOR":"6C0FF253",
	"xh":xh,
	"sfzh":sfzh,
	"kl":kl,
	"yzm":yzmstr}
scoreValues={"start":"0",
		"pageSize":"80"}
request=urllib2.Request(url,urllib.urlencode(values))        
scoreRequest=urllib2.Request(scoreurl,urllib.urlencode(scoreValues))  
f=opener.open(request)             #请求登陆页面
score=opener.open(scoreRequest)        #登陆成功的话就可以得到全部成绩
scorestr=score.read()
#正则表达式
restr='"kcmc":"(.*?)","jsxm":"(.*?)","xq":"(.*?)","xs":"(.*?)","xf":"(.*?)","zpcj":"(.*?)","pscj":"(.*?)","qmcj":"(.*?)","kcsx":"(.*?)","cjid":"(.*?)","ksfsm":"(.*?)","pxcj":"(.*?)"}'
pattern=re.compile(restr)
items=re.findall(pattern,scorestr)          #匹配元素
jd=0.0		#总绩点
xf=0.0		#总学分
for item in items:
	print item[0],item[1],item[2],item[3],item[4],item[5],item[6],item[7],item[8],item[9],item[10],item[11]
	if repr(getjd(item))!="None":
		jd=jd+float(repr(getjd(item)))
		xf=xf+float(item[4])
		print u"该课程学分绩点为:"+repr(getjd(item))
print u"所修课程学分绩点为:"+repr(jd)
print u"所修课程学分为  :"+repr(xf)
print u"平均学分绩点为  :"+repr(jd/xf)
print cj                     #SessionId




原文地址:https://www.cnblogs.com/A-yes/p/9894234.html