如何破解字体反爬机制

逆向工程实战:破解拼多多字体加密反爬机制 在Web数据抓取领域,字体加密是一种常见的数据混淆技术,其核心原理是通过自定义字体文件,将关键数据(如价格、销量)的真实字符映射到非标准编码的私用区字符上。这种技术利用浏览器能正确渲染自定义字体,而直接复制或查看源代码时却显示乱码的特性,有效阻碍了传统爬虫的数据提取。从技术价值看,理解并破解字体加密机制,不仅能提升数据采集的准确性和完整性,更是掌握Web逆向工程核心技能的关键。在电商价格监控、数据分析等应用场景中,面对如拼多多等平台广泛使用的动态字体反爬,工程师需要融合网络抓取、二进制解析和字体学知识,通过 阅读详情

        这几天爬取58租房信息的时候意外发现了它是一个字体反爬的网站,所谓的字体反爬就是网站将一些关键字替换为网站自己的字体,这样在网页上字体会正常显示,但是当爬取下来的时候,经过字体加密的字符都是乱码的,根本无法查看

如图所示:

可以看到,2390元/月在页面上是正常显示的,但是,当我们打开查看器查看的时候......

好端端的2390就变成了不知道什么字符.......

这就是网站使用了字体反爬机制,网站有自己的一套字体,只有在它的页面上才会正常显示,否则就是一串乱码,毫无价值。那么遇到这种问题该怎么解决,在经历几天的摸索之后终于将正确的信息抓取了下来。

首先,我们查看网页的源码,就是下面这样的

这是网页源码中一串base64的字符串,它就是网站的字体文件,很难想象一串base64的字符串就是它的字体文件。

我们将这一串base64的字符串复制下来,将它解码并保存成一个字体文件

import base64


font_face = "AAEAAAALAIAAAwAwR1NVQiCLJXoAAAE4AAAAVE9TLzL4XQjtAAABjAAAAFZjbWFwq8N/ZAAAAhAAAAIuZ2x5ZuWIN0cAAARYAAADdGhlYWQTcnjtAAAA4AAAADZoaGVhCtADIwAAALwAAAAkaG10eC7qAAAAAAHkAAAALGxvY2ED7gSyAAAEQAAAABhtYXhwARgANgAAARgAAAAgbmFtZTd6VP8AAAfMAAACanBvc3QFRAYqAAAKOAAAAEUAAQAABmb+ZgAABLEAAAAABGgAAQAAAAAAAAAAAAAAAAAAAAsAAQAAAAEAAOv6p7JfDzz1AAsIAAAAAADX9ZbuAAAAANf1lu4AAP/mBGgGLgAAAAgAAgAAAAAAAAABAAAACwAqAAMAAAAAAAIAAAAKAAoAAAD/AAAAAAAAAAEAAAAKADAAPgACREZMVAAObGF0bgAaAAQAAAAAAAAAAQAAAAQAAAAAAAAAAQAAAAFsaWdhAAgAAAABAAAAAQAEAAQAAAABAAgAAQAGAAAAAQAAAAEERAGQAAUAAAUTBZkAAAEeBRMFmQAAA9cAZAIQAAACAAUDAAAAAAAAAAAAAAAAAAAAAAAAAAAAAFBmRWQAQJR2n6UGZv5mALgGZgGaAAAAAQAAAAAAAAAAAAAEsQAABLEAAASxAAAEsQAABLEAAASxAAAEsQAABLEAAASxAAAEsQA"
# 太长没复制完......

b = base64.b64decode(font_face)
with open('58.ttf','wb') as f:
    f.write(b)

这里我们将它保存成一个ttf的字体文件,然后使用fontCreator将这个字体文件打开(fontCreator需要自行下载,直接百度就能下载类,非常简单)

打开之后的效果

我们再来看看网页上的源码......

小伙伴们是不是会惊奇的发现,网页源码上被替换掉的数字,使用fontCreator都能找到与之对应的原本的数字,那么立刻就能想到的一个方法就是将这些网页中的编码与原本的值对应成一个字典,只要抓取到了字典中存在的值就将其替换成本来的值,但是(注意我这里使用了但是)......

同样的,这也是58的一个字体文件,但是解析出来编码与对应的数字与上一次解析的完全不一样,这倒不是因为fontCreator解析出错,而是因为58这个网站友好几套字体文件,它的每一页的数据使用的都是随机的字体文件,当你解析了第一页字体的对应关系,拿小本本美滋滋的将对应关系记下来,但是点击到第二页的时候,发现关系又完全对不上,是不是很气。而且又不可能将每一页的对应关系都用本子记录下来。这时候就需要另一个工具,python的第三方库fontTools,直接pip安装就行。

在进行解密之前,先将原先的字体文件保存成一个xml文件。

from fontTools.ttLib import TTFont
font = TTFont('58.ttf')
font.saveXML('test.xml')

打开这个xml看看到底是啥

看不懂......

这个就好像有点懂了,code的值不是网页上的数字被替换的字符串吗!!!

这里的name属性的值实际对应的就是网页上的数字,下面的代码可以帮助我们查看对应关系

from fontTools.ttLib import TTFont
font = TTFont('58.ttf')
# font.saveXML('test.xml')
print(font.keys())

a = font['cmap'].tables[2].ttFont.getGlyphOrder()
b = font['cmap'].tables[2].ttFont.getReverseGlyphMap()
c = font['cmap'].tables[2].ttFont.tables['cmap'].tables[1].cmap
print("ppp ::::: ",a)
print("ddd ::::: ",b)
print("ddd ::::: ",c)

输出的结果

这里最后一行输出的就是网页上显示的字符串与camp标签中的name值的对应关系。那么网页上显示的0x958f这种字符串究竟是什么意思呢,它其实是一个十六进制的数字,将这个十六进制的数字转换成十进制(int("0x985f",16)),得到的值就是最后一行输出的键,那么这个键对应的值就是第二行输出的键,第二行的值就是本来的数据,这样一来,在抓取每一页之前,先抓取到它这一页的字体文件,进行分析,得到对应关系,不就能获取到原始的数据了嘛。

ps:需要注意的是,使用fontCreator解析时发现数字对应关系前面有一个空值,所以实际解析到的对应的数字需要减1才能得到正确的值。

代码思路:1.在爬取每一页数据之前,先获取到源码中的base64的字符串,解码,保存成字体文件2.生成对应关系的字典3.抓取到页面的乱码文字,解码成16进制的数字3.将十六进制的数字转为十进制,判断字典中是否有这个键,如果有,则解析为原本的数字,如果没有,则说明这个文字没有进行机密处理,保存原来的文字即可。4.完成全部加密文字的替换得到正确的数据。

实际代码:

import re
import lxml.html
import base64
from fontTools.ttLib import TTFont
import requests
import random
import sqlite3
db = sqlite3.connect("58.db")
cursor = db.cursor()

UA = [
    "Mozilla/5.0 (Macintosh; U; Intel Mac OS X 10_6_8; en-us) AppleWebKit/534.50 (KHTML, like Gecko) Version/5.1 Safari/534.50",
    "Mozilla/5.0 (Windows; U; Windows NT 6.1; en-us) AppleWebKit/534.50 (KHTML, like Gecko) Version/5.1 Safari/534.50",
    "Mozilla/5.0 (Macintosh; Intel Mac OS X 10.6; rv:2.0.1) Gecko/20100101 Firefox/4.0.1",
    "Mozilla/5.0 (Windows NT 6.1; rv:2.0.1) Gecko/20100101 Firefox/4.0.1"
]

headers = {
    "User-Agent":random.choice(UA)
}

def resp(i):
    base_url = "https://tj.58.com/pinpaigongyu/pn/{}/"
    response = requests.get(base_url.format(i), headers=headers)
    print("正在下载:",response.url)
    return response

def get_base64_str(response):
    base_font = re.compile("base64,(.*?)\'")
    base64_str = re.search(base_font, response.text).group().split(',')[1].split('\'')[0]
    return base64_str

def make_font_file(base64_str):
    b = base64.b64decode(base64_str)
    with open("58.ttf","wb") as f:
        f.write(b)

def make_dict():
    font = TTFont('58.ttf')
    b = font['cmap'].tables[2].ttFont.getReverseGlyphMap()  # 编码对应的数字
    c = font['cmap'].tables[2].ttFont.tables['cmap'].tables[1].cmap  # 页面的十六进制数对应的编码
    return b, c


def parse_title(text):
    s = ""
    title_re = re.compile("\s")
    html = lxml.html.fromstring(text)
    title = html.xpath('//div[@class="des strongbox"]/h2/text()')[0]
    title = re.sub(title_re,'',title)
    for i in title:
        encode_str = str(i.encode("unicode-escape")).split(r'\\u')[-1].replace('\'','').replace(r'b(','').strip()
        num, code = make_dict()
        if len(encode_str) != 4:
            i = i
        elif int(encode_str,16) not in code:
            i = i
        else:
            i = str(num[code[int(encode_str,16)]] - 1)
        s += i
    return s

def parse_price(text):
    s = ""
    html = lxml.html.fromstring(text)
    price_code = html.xpath('//span[@class="strongbox"]/b/text()')[0]
    price_code = price_code.strip().replace('\r\n','').replace(' ','')
    price_encode_str = str(price_code.encode("unicode-escape")).split('\'')[1].split('-')
    if len(price_encode_str) > 1:
        s1 = ""
        s2 = ""
        encode_list1 = price_encode_str[0].split(r"\\u")[1:]
        encode_list2 = price_encode_str[1].split(r"\\u")[1:]
        for i in encode_list1:
            price = int(i,16)
            num, code = make_dict()
            s1 += str(num[code[price]] - 1)
        for i in encode_list2:
            price = int(i,16)
            num, code = make_dict()
            s2 += str(num[code[price]] - 1)
        s = s1 + '-' + s2

    else:
        str_list = price_encode_str[0].split(r'\\u')[1:]
        for i in str_list:
            price = int(i,16)
            num, code = make_dict()
            s += str(num[code[price]]-1)
    return s

def parse_room(text):
    s = ""
    html = lxml.html.fromstring(text)
    p_rooms = html.xpath('//p[@class="room"]/text()')[0]
    room_re = re.compile('[\s]')
    room_re1 = re.compile(r'[m²]')
    room_re2 = re.compile(r'/')
    rooms = re.sub(room_re,'',p_rooms)
    rooms = re.sub(room_re1,"平米",rooms)
    rooms = re.sub(room_re2,"至",rooms)
    for i in rooms:
        encode_str = str(i.encode("unicode-escape")).split(r'\\u')[-1].replace('\'', '').replace(r'b/','').strip()
        # print(encode_str)
        num, code = make_dict()
        if len(encode_str) != 4:
            i = i
        elif int(encode_str,16) not in code:
            i = i
        else:
            i = str(num[code[int(encode_str,16)]] - 1)
        s += i
    return s

def parse_dist(text):
    s = ""
    html = lxml.html.fromstring(text)
    p_dist_re = re.compile('\skm')
    try:
        p_dist = html.xpath('//p[@class="dist"]//text()')[1]
        p_dist = ''.join(p_dist).replace(' ','')
        p_dist = re.sub(p_dist_re,'千米',p_dist)
        for i in p_dist:
            encode_str = str(i.encode("unicode-escape")).split(r'\\u')[-1].replace('\'', '').replace(r'\\r','').replace(r'\\n','').replace(r'b.','').strip()
            num, code = make_dict()
            if len(encode_str) != 4:
                i = i
            elif int(encode_str, 16) not in code:
                i = i
            else:
                i = str(num[code[int(encode_str, 16)]] - 1)
            s += i
        dist = s
    except:
        dist = "暂无"
    return dist

def short_rent(text):
    html = lxml.html.fromstring(text)
    try:
        rent = html.xpath('//p[@class="room"]/b/text()')[0]
    except:
        rent = "不可短租"
    return rent

def parse_li(response):
    li_re = re.compile('<li logr([\s\S]*?)</li>')
    li_list = re.findall(li_re,response.text)
    return li_list

def parse_target(text):
    html = lxml.html.fromstring(text)
    try:
        target = html.xpath('//p[@class="spec"]/span/text()')
        target = ','.join(target)
    except:
        target = "暂无"
    return target

if __name__ == '__main__':
    for i in range(1,171):
        response = resp(i)
        base64_str = get_base64_str(response)
        make_font_file(base64_str)
        make_dict()
        li_list = parse_li(response)
        for i in li_list:
            title = parse_title(i)
            price = parse_price(i)
            room = parse_room(i)
            dist = parse_dist(i)
            rent = short_rent(i)
            target = parse_target(i)
            city = "天津"
            cursor.execute("insert into home(title, price, room, dist, rent,target, city) values (?,?,?,?,?,?,?)",[title,price,room,dist,rent,target,city])
            db.commit()

 

由于我的正则表达式功底有点差,所以这里的正则表达式都用的是比较low的..........

但是数据爬下来了,而且没有问题

一次愉快的破解字体反爬机制就到此结束了

 

Python爬虫实战:破解字体反爬机制与WOFF字体解析 静态字体:通过fonttools解析Unicode,手动构建映射表,效率高;动态字体:通过Pillow渲染字形,自动匹配标准字符,适配性强;实战整合:结合异步请求、缓存、动态适配,实现端到端的反爬破解。本文的方案可适配绝大多数字体反爬场景,进阶方向可探索「AI字形识别」(如CNN识别字形)、「批量字体解析」(处理多网站反爬)等,进一步提升破解的自动化和准确率。 阅读详情

相关推荐

深度实战:Python爬虫破解猫眼电影票房排行字体反爬机制

在爬虫学习领域,猫眼电影是一个经典得不能再经典的案例。字体反爬。字体反爬是近年来国内主流网站(猫眼、大众点评、天眼查等)常用的反爬策略。它通过自定义字体文件将正常的数字或文字映射成特殊字符,使得爬虫直接抓取到的HTML内容是一堆“乱码”,而真实数据只有在浏览器渲染后才能正确显示。这种技术对传统基于正则表达式、XPath的爬虫造成了巨大挑战。

2201_76125261的博客 510

字体反爬破解

通过观察可以得出:网页显示后四位与xml中的code值后四位一样,对应的name值看起来也是unicode编码,也是拿后四位去验证。xml中的name值:uni5DE5 uni7A0B uni5E08。一般常见的为:ttf、eot、otf、woff、svg,可以使用。xml中的code值:0xed53 0xea63 0xe4e5。这里判断正确无误,底层通过css转换就是这个文件的文字。关闭对应的css样式可以看到,确实是做了字体反爬。例如 这里python工程师。网页显示:  。

makyking 2032

爬虫反爬:字体反爬案例分析与爬取实战

字体反爬是一种常见的反爬虫技术,通过自定义字体文件(如TTF、WOFF)对网页中的字符进行加密或替换,将页面上的文字使用特殊字体显示,而爬虫在解析时由于缺少相应的字体文件,导致无法正确识别文字内容。本文将深入分析字体反爬的机制,并提供实战样例,帮助读者理解和应对这一挑战。字体反爬技术通过自定义字体文件对字符进行加密或替换,增加了爬虫解析的难度。通过下载并解析字体文件,建立字符映射关系,可以有效破解这种反爬机制。在实际应用中,可能需要结合动态加载、CSS偏移等其他反爬技术进行综合处理。

数据知道的博客 1万+

58同城 反爬虫机制及处理

58同城 反爬虫机制及处理 字体反爬机制 问题: 字体反爬也就是自定义字体反爬通过调用自定义的ttf文件来渲染网页中的文字,而网页中的文字不再是文字,而是相应的字体编码,通过复制或者简单的采集是无法采集到编码后的文字内容!必须通过程序去处理才能达到采集成本。 网页显示与源代码出现不一致的情况 这里58同城将数字(比较敏感的元素,包括价格,面积大小)用自定义的ttf文件进行了渲染(该文件base64进行加密,包含数字到相应的unicode字符之间的映射信息),从而产生类似于乱码的情况。 Base64

qq_45612184的博客 6973

我去!爬虫遇到字体反爬,哭了

大家好,我是辰哥今天准备爬取某某点评店铺信息时,遇到了『字体』反爬。比如这样的:还有这样的:可以看到这些字体已经被加密(反爬)竟然遇到这种情况,那辰哥就带大家如何去解决这类反爬(字体反爬类...

公众号:Python研究者 888

爬虫字体反爬的解决(三)

代码中没涉及太多的注释,一方面是考虑到爬虫能学到这一步,相信大家能力是足够的;另一方面也是为了让大家能够自己探求每一行代码在程序中的功能,所以只提供代码和大致思路,具体的理解就依靠大家自己了。

Mr.Fu的博客 2063

字体反爬慢慢总结破解方式

慢慢的将破解方法搞定都行啦样子与打算。

kuxingseng123的博客 1186

58同城 (全国) 房屋信息爬虫.zip

爬虫(Web Crawler)是一种自动化程序,用于从互联网上收集信息。其主要功能是访问网页、提取数据并存储,以便后续分析或展示。爬虫通常由搜索引擎、数据挖掘工具、监测系统等应用于网络数据抓取的场景。 爬虫的工作流程包括以下几个关键步骤: URL收集: 爬虫从一个或多个初始URL开始,递归或迭代地发现新的URL,构建一个URL队列。这些URL可以通过链接分析、站点地图、搜索引擎等方式获取。 请求网页: 爬虫使用HTTP或其他协议向目标URL发起请求,获取网页的HTML内容。这通常通过HTTP请求库实现,如Python中的Requests库。 解析内容: 爬虫对获取的HTML进行解析,提取有用的信息。常用的解析工具有正则表达式、XPath、Beautiful Soup等。这些工具帮助爬虫定位和提取目标数据,如文本、图片、链接等。 数据存储: 爬虫将提取的数据存储到数据库、文件或其他存储介质中,以备后续分析或展示。常用的存储形式包括关系型数据库、NoSQL数据库、JSON文件等。 遵守规则: 为避免对网站造成过大负担或触发反爬虫机制,爬虫需要遵守网站的robots.txt协议,限制访问频率和深度,并模拟人类访问行为,如设置User-Agent。 反爬虫应对: 由于爬虫的存在,一些网站采取了反爬虫措施,如验证码、IP封锁等。爬虫工程师需要设计相应的策略来应对这些挑战。 爬虫在各个领域都有广泛的应用,包括搜索引擎索引、数据挖掘、价格监测、新闻聚合等。然而,使用爬虫需要遵守法律和伦理规范,尊重网站的使用政策,并确保对被访问网站的服务器负责。

实战解密:如何用Python爬虫破解大众点评动态字体加密与反爬机制

当你在进行市场分析、竞品研究或用户行为洞察时,是否曾被大众点评的反爬机制所困扰?面对动态字体加密、Cookie验证、请求频率限制等多重防护,传统爬虫往往束手无策。今天,我们将深入剖析一个实战型解决方案——一个能够稳定获取全站数据、智能应对反爬挑战的Python爬虫框架。 ## 场景一:破解动态字体加密,实现精准数据提取 大众点评采用了先进的动态字体加密技术来保护其数据,这是许多爬虫开发者遇到的

gitblog_00106的博客 441

Python爬虫实例:爬取猫眼电影——破解字体反爬

字体反爬 字体反爬也就是自定义字体反爬,通过调用自定义的字体文件来渲染网页中的文字,而网页中的文字不再是文字,而是相应的字体编码,通过复制或者简单的采集是无法采集到编码后的文字内容的。 现在貌似不少网站都有采用这种反爬机制,我们通过猫眼的实际情况来解释一下。 下图的是猫眼网页上的显示: 检查元素看一下 这是什么鬼,关键信息全是乱码。 熟悉 CSS 的同学会知道,C...

weixin_30408675的博客 1172

Python入门基础教程(非常详细)

Python是一门开源免费、通用型的脚本编程语言,它上手简单,功能强大,坚持「极简主义」。Python类库(模块)极其丰富,这使得Python几乎无所不能,不管是传统的Web开发、PC软件开发、Linux运维,还是当下火热的机器学习、大数据分析、网络爬虫,Python都能胜任。这套Python基础教程不是教科书,不会玩弄概念,而是力求口语化和通俗化,让读者尽快入门。如果有小朋友出于兴趣学习Python,请引导他阅读本教程的前半部分,这是基础,可以降低学习成本;...

Yuki1127918的博客 34万+

猫抓Cat-Catch 浏览器资源嗅探扩展:3 步装好,从安装到下载视频完整指南

想离线保存一整套网课,却发现播放列表里只有一个 28 秒的封面片段?打开开发者工具翻 Network,满屏都是看不懂的短链接。这就是**猫抓 Cat-Catch** 想解决的问题:它是一个浏览器资源嗅探扩展,自动列出网页里所有能下载的视频、音频和 M3U8 流媒体,让你直接勾选下载。 ## 这是什么 · 能做什么 一句话定位:装在浏览器里的"媒体资源清单",把网页正在加载的媒体文件抓出来、列出

gitblog_00332的博客 1820

玩转肺癌目标检测数据集Lung-PET-CT-Dx ——①从TCIA获取影像数据集

该目标检测公共数据集源自 The Cancer Imaging Archive(TCIA),是肿瘤研究方面的著名的医学影像公开数据库。 数据以 DICOM 格式存储,由肺癌受试者的 CT 和 PET-CT DICOM 图像组成。

takedachia的博客 1万+

爬虫字体反爬的解决(一)

学习了前边的爬虫知识,大家一定爬取过很多的网站了,也一定被很多网站的各式各样的反爬机制劝退过,那么这些反爬机制如何来破解,大家也一定想破了头,本节课,我们来搞点不同寻常的有深度的事情——破解字体反爬!大家看目录,发现我把字体反爬分了多个章节,可想而知字体反爬的“困难程度”,但是不要紧,我们会把目前的字体反爬技术一一给大家讲解!

Mr.Fu的博客 2214

url中能出现的字符_python爬虫,解决大众点评字符库反爬机制的经验

刚开始写文章还希望大家可以喜欢,对于爬虫只是个人整理出的方法,爬虫大牛请嘴下留情。“”仅限学术交流,如有冒犯请联系作者删除“”话不多说,想分析天津地区餐饮行业的大致情况,要爬出(商铺名称,星级,评价条数,人均消费金额,菜系,商圈,团购活动等)。可是在爬虫时发现,这些数字都是以这类方框形式展示,再看源代码,以&#xXXXX这种形式展示,这是反爬机制中的字体库反爬,要把这些代码转化成前端看到的...

weixin_30651345的博客 230

STM32CUBEMX | STM32L431RCT6的内部Flash操作

一、STM32CUBEMX配置 1、选择芯片型号: 2、配置时钟源 1、 如果选择使用外部高速时钟(HSE),则需要在System Core中配置RCC; 2、 如果使用默认内部时钟(HSI),这一步可以略过; 3、配置时钟树 STM32L4的最高主频到80M,所以配置PLL,最后使HCLK = 80Mhz即可: 4、代码生成设置 点击GENERATE CODE即可生成MDK-V5工程: 二、在MDK中编写、编译、下载用户代码 1、STM32内部Flash及HAL库API 查看所使用芯片的信息,

yongridada的博客 5541

取出url中的字符_python爬虫,解决大众点评字符库反爬机制的经验

刚开始写文章还希望大家可以喜欢,对于爬虫只是个人整理出的方法,爬虫大牛请嘴下留情。“”仅限学术交流,如有冒犯请联系作者删除“”话不多说,想分析天津地区餐饮行业的大致情况,要爬出(商铺名称,星级,评价条数,人均消费金额,菜系,商圈,团购活动等)。可是在爬虫时发现,这些数字都是以这类方框形式展示,再看源代码,以&#xXXXX这种形式展示,这是反爬机制中的字体库反爬,要把这些代码转化成前端看到的...

weixin_40005373的博客 282

飞塔防火墙和paloalto防火墙构建ipsec

一、配置fortigate防火墙1.防火墙配置上网功能1.1配置fortigate的wan1接口IP为100.100.100.2/24VLAN交换internal,IP地址为192.168.156.99/24。开启DHCP分配IP地址范围为192.168.156.110-192.168.156.2101.2配置访问互联网的缺省路由1.3配置访问互联网的安全策略2.配置与Paloalto防火墙的IPSECVPN。

weixin_44675999的博客 3710

大众点评数据采集终极解决方案:破解动态字体加密与反爬机制

在大数据时代,餐饮行业的数据分析已成为市场决策的关键支撑。然而,获取大众点评这类平台的完整数据却面临着严峻的技术挑战。动态字体加密、反爬机制、Cookie验证等层层防护,让许多数据工程师望而却步。今天,我们将深入探讨一个专业级的大众点评爬虫解决方案,它不仅能够稳定获取全站数据,更成功破解了动态字体加密这一核心技术难题。 ## 🔍 数据采集的三大技术痛点 ### 痛点一:动态字体加密的破解难题

gitblog_01153的博客 910

字体反爬是什么?如何解析 “乱码” 文字内容?

【摘要】字体反爬是网站通过自定义字体篡改编码与字形关系,使爬虫获取乱码而用户正常浏览的技术手段。解析需四步:1)识别反爬特征;2)获取字体文件;3)分析编码-字形映射(使用fonttools等工具);4)替换乱码为真实内容。关键需注意法律合规性及应对动态更新的字体文件,核心在于还原被篡改的编码对应规则。该技术多见于电商价格、阅读量等数据保护场景。

weixin_41943766的博客 1438

SIWAVE+ADS提取PCB走线寄生参数

本文将介绍一种很适合PCB走线提取寄生电感等参数的方法,即是通过SIWAVE将PCB走线的S参数提取出来,再通过ADS将S参数转换成电感、电容值。

sinat_15150363的博客 1715
上一篇: 通过ajax接口爬取智联招聘
下一篇: Scrapy与Twisted
评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值