整合营销服务商

电脑端+手机端+微信端=数据同步管理

免费咨询热线:

Python每日一练-用Python制作mini翻译器

  • 1. 实例描述
  • 2. 技术要点
    • 2.1 有道词典这样的 JS 混淆加密应该怎么破
  • 3. 代码实现


1. 实例描述

在平时编程的过程中,会经常在网上翻译一些单词,本文使用Python制作一款翻译小工具,不仅可以自己用,还可以嵌入到程序当中。运行程序,效果如下图所示,在文本框输入英文或中文,单击 翻译 按钮即可翻译,并将翻译内容显示在下面的文本框中。单击 保存 按钮将输入内容和翻译内容保存到文本文件中以便日后复习。单击 清空 按钮,将清除文本框中的内容。

2. 技术要点

利用 requests 模块获取 有道词典web 页面的 post 信息,获取需要的内容,通过 tkinter 模块生成窗口界面,使用文件读写方法将内容保存到文本文件中。

2.1 有道词典这样的 JS 混淆加密应该怎么破

嘿嘿嘿,本文需要说说一些爬虫过程中需要斗智斗勇的事情了,这次咱们就来说说关于一些 JS 混淆加密的事。所谓 JS ,就是 JavaScript,一种前端的脚本语言,一般情况下每个网站都需要 JS 来做一些数据交互,页面渲染等一些异步操作。当然,对于反爬的人来说,JS 的用处还可以用来对一些数据进行加密。

今天咱们就以有道词典这个在线翻译的网站为例,看看他们是如何加密请求数据的,以及笔者是如何通过 Python 模拟请求从而获得关键数据的。

点击 此处 打开有道翻译的网站:

输入中文然后点击翻译按钮就会翻译出来英文,比如:

接着我们打开开发者工具,按下 F12 来抓一下数据,当我们点击翻译的时候,可以看到有了一个请求:

点进去看可以发现,POST 请求的地址是:

http://fanyi.youdao.com/translate_o?smartresult=dict&smartresult=rule
1

我们再来看一下请求过去携带的参数是啥:

可以看到,还是需要挺多参数的,其中的 i 就是我们要翻译的内容,那简单啊~想要得到翻译后的数据,那么我们直接把请求头和所需参数的值复制一下,然后用 requests 请求一波不就搞定了?运行一波,返回的是错误码。

我们再点多几次翻译按钮,然后就可以看到有多次请求。

可以发现,每一次的请求中的 salt、sign、lts、bv 参数是会一直变化的。

我们回到 NetWork ,我们看到 Initiator 这一栏,可以看到它请求到了 fanyi.min.js:1 这个 js 文件。

我们就点 fanyi.min.js:1 进去看看,牛的一比,直接看不懂…还好,左下角有一个 {} ,可以点一下,发现有惊喜,直接帮我们把压缩的 js 代码格式化。

牛逼不,行号都给我们显示出来了,不过到了这里,依然懵逼,我们还是不知道怎么拿到 salt、sign、lts、bv 这些参数的值…咋办?恩,Chrome 浏览器的打断点功能在这个时候就要派上用场。那么如何使用断点功能呢,我们看到 Chrome 的右边是这样的:

看到这个 XHR/fetch BreakPoints 没,在这里我们可以添加 url ,根据请求这个 url 打断点。而我们要打的断点就是一开始获取到的请求 url :

http://fanyi.youdao.com/translate_o?smartresult=dict&smartresult=rule
1

点击 XHR/fetch BreakPoints 右边的 + 号,然后把链接复制进去:

这时候再点击翻译按钮,突然,你的屏幕一灰,表示好事将近,我们成功打上了断点,也就是说,现在我们可以在请求之前做一些骚操作。

这时候我们将右边的 Call Stack 展开,点 t.translate 进去:

这些,就是我们在点击翻译按钮之后,会调用到 js 里面的方法,从这里下手,来寻找参数是被如何加密的,

3. 代码实现

用Python制作mini翻译器的具体步骤如下:

  1. 首先安装 requests 模块。使用 pip 命令安装,命令如下:pip install --user -i http://pypi.douban.com/simple --trusted-host pypi.douban.com requests 1
  2. 导入相关模块,代码如下。import tkinter as tk import requests import time import hashlib import random 12345
  3. 定义翻译函数,代码如下。def get_ts(): """ 获取时间戳 :return: 时间 """ return str(int(time.time() * 1000)) def get_bv(): """ 获取app版本 并通过md5加密 :return: 加密后的字符串 """ navigator_appVersion = 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3' \ '904.108 Safari/537.36' m = hashlib.md5() m.update(navigator_appVersion.encode('utf-8')) return m.hexdigest() def get_salt(ts): return str(ts) + str(int(random.random() * 10)) def get_sign(salt): str1 = text1.get() # 定义一个变量,用来接收输入文本框的值 str_data = 'fanyideskweb' + str1 + salt + ']BjuETDhU)zqSxf-=B#7m' m = hashlib.md5() m.update(str_data.encode('utf-8')) return m.hexdigest() def get_form_data(): str1 = text1.get() # 定义一个变量,用来接收输入文本框的值 ts = get_ts() salt = get_salt(ts) form_data = { 'i': str1, 'from': 'AUTO', 'to': 'AUTO', 'smartresult': 'dict', 'client': 'fanyideskweb', 'salt': str(salt), 'sign': get_sign(salt), 'ts': ts, 'bv': get_bv(), 'doctype': 'json', 'version': '2.1', 'keyfrom': 'fanyi.web', 'action': 'FY_BY_CLICKBUTTION', } return form_data # 定义翻译函数 def translate(): url = "http://fanyi.youdao.com/translate_o?smartresult=dict&smartresult=rule" headers = { 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36', 'Referer': 'http://fanyi.youdao.com/', 'Cookie': 'OUTFOX_SEARCH_USER_ID_NCOO=173326173.72226533; OUTFOX_SEARCH_USER_ID="-1202396372@10.108.160.18"; DICT_UGC=be3af0da19b5c5e6aa4e17bd8d90b28a|; JSESSIONID=abcAjF-mxbKFQ_48uyLpx; __guid=204659719.1682486053682624500.1597281254731.5474; monitor_count=2; ___rl__test__cookies=1597285713766' } response = requests.post(url=url, data=get_form_data(), headers=headers) if response.status_code == 200: result = response.json() translate_result = result['translateResult'][0][0]['tgt'] text2.delete(1.0, "end") # 清空输出文本框 text2.insert('end', translate_result) # 将翻译结果添加到输出文本框中 1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768
  4. 定义写入文本 txt 的函数,代码如下。# 定义写入文本txt的函数 def write(): f1 = open('translate.txt', 'a+') f1.write(text1.get() + ',' + text2.get(0.0, tk.END)) 1234
  5. 定义清空文本框的函数,代码如下。# 定义清空文本框的函数 def delete(): text1.delete(0, "end") # 从第一行清除到最后一行 text2.delete(1.0, "end") 1234
  6. 窗口界面设计,代码如下。if __name__ == '__main__': window = tk.Tk() # 创建window窗口 window.wm_attributes("-topmost", 1) # 置顶 window.title("AmoXiang mini翻译器") # 定义窗口名称 window.resizable(width=False, height=False) # 决定框体大小是否能够调整 text1 = tk.Entry(window, width=80, bg='whitesmoke') # 在窗体上添加一个输入文本框,并设置尺寸和颜色 text2 = tk.Text(window, height=18, bg='lightgrey') # 在窗体上添加一个输出文本框,并设置尺寸和颜色 text1.grid(row=0, sticky="W", padx=1) text2.grid(row=1) # 添加一个按钮,用于触发翻译功能 t_button = tk.Button(window, text='翻译', relief=tk.RAISED, width=8, height=1, font='宋体', bg='red', fg='white', command=translate) # 添加一个按钮,用于触发清空输入文本框 button1 = tk.Button(window, text='保存', font='宋体', relief=tk.RAISED, width=8, height=1, command=write) # 添加一个按钮,用于触发清空输出文本框 button2 = tk.Button(window, text='清空', font='宋体', relief=tk.RAISED, width=8, height=1, command=delete) # 添加背景图片 image_file = tk.PhotoImage(file='amo.gif') label = tk.Label(window, image=image_file) # 完成界面布局,设置各个控件的位置 t_button.grid(row=0, column=1, padx=2) button1.grid(row=0, column=2, padx=2) button2.grid(row=0, column=3, padx=2) label.grid(row=1, column=1, columnspan=3) tk.mainloop() 12345678910111213141516171819202122232425

至此今天的案例就到此结束了,笔者在这里声明,笔者写文章只是为了学习交流,以及让更多学习Python基础的读者少走一些弯路,节省时间。

最后,小编想说:我是一名python开发工程师,

整理了一套最新的python系统学习教程,

想要这些资料的可以关注私信小编“01”即可(免费分享哦)希望能对你有所帮助

记得智趣狗去年体验的戴尔新游匣7466吗(点击查看《戴尔新游匣7466游戏本体验》)?如今游匣系列已经全面进化到了七代酷睿和NVIDIA GTX1050系列独显时代,整体性能较前辈们又有了进一步的提升。

没错,今天智趣狗为大家带来的体验产品,就是游匣系列的最新款:Master 7000-15,拥有15.6英寸大视野,同时还融入了跑车元素外观设计,并选择i7-7700HQ与GTX1050 Ti搭配的游戏悍将。

这次智趣狗拿到的戴尔游匣Master 15为超跑版,此外该机器还有赤红版和湛黑版两种配色,小伙伴们可以根据自己的喜好加以选择。三种版本的差异只是A面的颜色和装饰,超跑版在赤红版的基础上添加了三道条纹,看起来更酷更时尚。

今天的体验,就先从游匣Master 15超跑版的外观赏析说起吧。

这次流行超跑风

如果你的流量足够,推荐播放这个实物图赏的视频,很好看哦。

手机用户可以点击 https://v.qq.com/x/page/s03927j34vj.html 查看视频

游匣Master 15依旧采用了金属材质的顶盖和边框,看起来就像是将整个机身“包裹”了起来,并在金属表面进行了类肤材质的红色喷涂工艺,不仅保证了机身整体的强度,也提升了手感,还能起到防滑效果。

超跑风格的A面装饰,喜欢吗?

游匣Master 15红色的金属侧边还采用了弧度处理,而不是游戏本上常用的那种棱角分明的刚毅风格,拎起笔记本时的手感也是杠杠的。

机身前端的红黑色栅格里隐藏着扬声器。

机身后面的散热框体是新游匣系列的点睛之笔,倾斜的切角让本来有点圆润感觉的机身也有了几分刚毅之感,两个“水”字型的栏栅后面就是被喷上红漆的散热鳍片,看起来非常个性。

游匣Master 15采用了游戏本中常用的红色键盘背光,但它却在WASD四个按键的边框上加入了一圈镂空处理,当红色背光亮起时,其他按键只有键帽上的标识可以透过红色炫光,而WASD的感觉则是被红光包裹,看起来更为醒目。

游匣Master 15的接口平均分布在机身两侧,对一款15.6英寸大屏游戏本来说,它的接口数量和种类不算特别丰富。

拆机只需一颗螺丝

为了方便玩家升级维护,戴尔为游匣Master 15准备了简易的拆机设计:只需拧下一颗螺丝,就能拆下底部的挡板。

游匣Master 15重约2.65kg,在15.6英寸游戏本中算不上轻盈的,也许很多童鞋会觉得有些遗憾。但小编想说的是,游匣Master 15重一点自有道理,那就是它在内部添加了防滚架结构,虽然增加了重量,但对机身坚韧性所起到的贡献却不容忽视。要知道,这年头绝大多数游戏本的主板、上面的芯片电容等都是直接裸露的,仅靠机身边框承担抗冲击的作用。

有了防滚架后,戴尔游匣Master 15的抗冲击性和耐挤压性,在同类产品中可以算是鲜有敌手了。值得一提的是,游匣Master 15对内部的每一颗螺丝,每一根排线都有注释说明,便于我们后期的深度拆机,细节设计值得称道。

这款机器标配128GB SSD和500GB HDD。可惜,游匣Master 15标配的SSD为SATA通道,读写性能相对一般。

戴尔游匣Master 15采用了双风扇双热管的散热模块,CPU和GPU双烤机测试时,处理器最高温度为95度,显卡温度为75度。请放心,CPU温度虽高但却不会出现降频问题,此时键盘中间偏右上的位置略有热感,整体表现还是很不错的。

GTX1050Ti是动力之源

戴尔游匣Master 15在配置上的最大亮点,就是选择了GTX1050 Ti独显与七代酷睿处理器搭配。关于GTX1050 Ti咱们需要再重点说一下,因为它算是NVIDIA新一代显卡中的神U(GPU)。

简单来说,笔记本用的GTX1050 Ti移动版和桌面显卡版的GTX1050规格一致,只是调低了功耗墙阈值,无法长时间满血运行在最高频率上而已。

GTX1050 Ti移动版的性能,可略微领先NVIDIA上一代移动显卡中的GTX970M,在1080P+中高画质下可以流畅运行时下所有的大型3D游戏。当然,如果你非外接显示器挑战2K甚至4K分辨率,那就免谈了。

最关键的是,GTX1050 Ti的TDP功耗仅有50W,和NVIDIA上一代定位中端的GTX960M持平,对散热模块的要求不算很高。

就我们体验的这款戴尔游匣Master 15来说,i7-7700HQ、GTX1050 Ti、双硬盘的组合几乎不存在性能上的瓶颈。可惜,该产品虽然性能给力,但它依旧没能用上IPS屏幕,垂直可视角度偏低是它的最大缺陷。

高颜值的实力派

总的来说,戴尔游匣Master 15是一款主打颜值的实力派选手,它足以满足绝大多数用户在方寸之间体验大型3D游戏的实力,个性的外观和简易的拆机升级设计也是它的特色之笔。如果你觉得这款Master 15价格较高,还可考虑搭载i5-7300HQ的低配版;如果你对游戏性能要求不算特别苛刻,还可考虑配备GTX1050显卡的Master 15,价格更实惠。

更多实物图片欣赏:

 在日常生活中,会有容易把合页与滑撑弄混,实质上合页与滑撑的区别是相当大。今天小编就帮大家好好区分一下合页与滑撑,不要再搞混了。

  合页与滑撑虽然都是门窗五金的重要组成部分,但它们在功能和使用上却存在显著的差异。了解这些差异,对于正确选择和安装门窗配件至关重要。

别再弄混了,合页与滑撑的区别_雄进五金

  合页,也被称为铰链,主要用于固定和连接门框和门扇,使门扇能够顺畅地打开和关闭。它通常由两片或多片金属片组成,通过转轴或连杆结构实现转动功能。合页的种类繁多,如普通合页、弹簧合页、轴承合页等,每种都有其特定的用途和优势。

  相比之下,滑撑则主要用于支撑和固定门窗,防止其变形和摇晃,多用于平开窗或上悬窗。它通常安装在门窗的框体上,通过滑轨和滑块的配合,实现门窗的开启和关闭,其材质多为304不锈钢。此外,滑撑的结构相对复杂,包括滑轨、滑块、托臂等多个部件,这些部件共同协作,确保门窗的稳定性和安全性。

  通过上述了解,合页和滑撑在门窗五金配件中各自扮演着不同的角色。因此,在选择和安装门窗配件时,需要根据实际需求,仔细区分合页和滑撑的功能和用途,以确保门窗的质量和使用效果。

  企业名称:广东雄进金属制品有限公司

  来源于:“ 雄进五金 ”:https://www.gd-xiongjin.com/article/detail/post-488.html