学 Python 有段时间的朋友是不是常遇到这种情况?用 Pandas 处理几万行数据就卡得不行,写的循环代码跑半小时还没结果;用 Scrapy 爬复杂网站,要么被反爬机制拦住,要么数据爬不全,想加个代理池却不知道从哪下手。别着急,兔子哥当初从基础转到进阶时,光是搞懂 Pandas 的矢量化操作和循环的区别就花了好几天,用 Scrapy 写中间件时还因为信号机制没搞明白,调试了整整两天。今天就带大家详解 Pandas 和 Scrapy 的高级用法,从实战技巧到避坑指南,帮你从入门迈向精通,一起往下看吧!
一、Pandas 高级用法:告别卡顿,处理数据效率翻倍
Pandas 基础用法大家可能都会,但遇到大数据或复杂分析就容易卡壳,这几个高级技巧能帮你效率提升 10 倍。
- 矢量化操作:别再用循环遍历数据
新手处理数据爱用for循环一行行操作,比如给某列数据加 10:for i in range(len(df)): df['score'][i] += 10
这种写法在数据量大时特别慢。高级用法是用矢量化操作,直接对整列处理:df['score'] += 10
原理是 Pandas 底层用 C 实现,整列操作比 Python 循环快得多。实测处理 10 万行数据,矢量化操作只用 2 秒,循环却要 1 分钟! - 分组聚合:复杂数据分析一键搞定
想按类别统计数据?比如按 “地区” 分组算平均销量,基础用法可能用groupby加mean,但高级用法能玩出更多花样:
`# 按地区分组,同时算销量的平均、最大和总和
region_stats = df.groupby('region')['sales'].agg(['mean', 'max', 'sum'])
给结果列重命名,更清晰
region_stats.columns = [' 平均销量 ', ' 最高销量 ', ' 总销量 ']
还能自定义聚合函数,比如算每个地区销量超过1000的比例,用agg` 搭配 lambda 函数超方便。- 缺失值处理:不止 dropna 和 fillna
基础用法删缺失值(dropna)或填默认值(fillna),但高级场景要更灵活:
- 用相邻值填充:
df['price'].fillna(method='ffill')# 用前一行值填充 - 按组填充缺失值:
df['score'] = df.groupby('class')['score'].transform(lambda x: x.fillna(x.mean()))# 用同班级平均分填缺失 - 检测异常缺失:
missing = df.isnull().sum() / len(df)# 算每列缺失比例,超过 的列直接删掉
不过话说回来,矢量化操作在大多数情况下比循环快,但如果是极复杂的自定义逻辑,偶尔用
apply也不是不行,关键看数据量和逻辑复杂度。二、Scrapy 高级用法:搞定反爬,爬虫更稳更强
Scrapy 爬简单网站没问题,但遇到反爬、需要复杂数据处理时,就得用高级功能了,这几个技巧企业实战常用。
- 中间件:反爬和数据预处理的关键
中间件能在请求发送前或响应回来后做处理,最常用的是反爬中间件:
- 随机 User-Agent:在
settings.py配置USER_AGENT_LIST,写个中间件随机选一个,避免被识别为爬虫。 - 代理中间件:爬频繁时加代理,在
process_request方法里给请求加proxy参数,比如request.meta['proxy'] = 'http://ip:port'。 - 重试中间件:遇到 403、503 响应时自动重试,在
settings设RETRY_TIMES = 3,搭配中间件判断状态码。
- 信号机制:灵活控制爬虫生命周期
Scrapy 有很多内置信号,比如爬虫启动、关闭时触发操作,比如爬完后自动保存数据到数据库:
python
from scrapy import signalsfrom scrapy.signalmanager import dispatcherclass MySpider(scrapy.Spider):def __init__(self):dispatcher.connect(self.spider_closed, signal=signals.spider_closed)def spider_closed(self, spider):# 爬虫关闭时执行,比如关闭数据库连接 self.db.close()这种机制能让爬虫更灵活,但信号之间的调用顺序比较复杂,具体哪些信号先触发,可能还需要进一步研究。
- 分布式爬虫基础:多线程爬取提速
单爬虫爬大量数据太慢?可以用 Scrapy-Redis 做分布式,多个爬虫共享一个任务队列。核心是在settings配置 Redis 地址,把SCHEDULER换成scrapy_redis.scheduler.Scheduler,这样多台机器能同时爬,效率翻倍。
三、实战案例:Pandas+Scrapy 结合,从爬取到分析全流程
光说不练假把式,用一个电商数据爬取分析案例,看看两者怎么结合用。
- 步骤 1:用 Scrapy 爬电商商品数据
目标:爬取某电商平台的手机商品信息(名称、价格、销量、评论数)。
- 写 Spider 解析商品列表页,用
XPath或CSS提取数据。 - 加代理中间件和随机 User-Agent,避免被封 IP。
- 用
ItemLoader处理数据清洗,比如价格去除 “¥” 符号转数字。
- 步骤 2:用 Pandas 分析爬取的数据
爬回数据存成 CSV 后,用 Pandas 分析:
- 数据清洗:处理缺失值(销量为 “暂无” 的填 0)、转换数据类型(价格转 float)。
- 分析热销商品:按价格分组,算每组的平均销量,找出性价比高的区间。
- 可视化:用
plot画销量和价格的散点图,看看价格和销量的关系。
代码片段参考:
python
# 读取爬取的数据 df = pd.read_csv('phone_data.csv')# 清洗价格列 df['price'] = df['price'].str.replace('¥', '').astype(float)# 按价格分组(每1000元一组) df['price_group'] = pd.cut(df['price'], bins=[0, 1000, 2000, 3000, 5000], labels=['0-1k', '1k-2k', '2k-3k', '3k-5k'])# 算每组平均销量 group_sales = df.groupby('price_group')['sales'].mean()group_sales.plot(kind='bar') # 画柱状图 四、避坑指南:进阶路上最容易踩的 5 个坑
- Pandas 链式赋值警告
新手常写df['a'][df['b']>10] = 0,会报SettingWithCopyWarning。解决方法:用loc定位,df.loc[df['b']>10, 'a'] = 0,避免链式操作。 - Scrapy 中间件不生效
写了中间件却没效果?检查settings.py里有没有配置DOWNLOADER_MIDDLEWARES,并给中间件设正确的优先级(数字越小越先执行)。 - Pandas 内存溢出
处理百万行数据时内存不够,用dtype指定数据类型,比如字符串列用category类型,整数用int32代替默认的int64,能省不少内存。 - Scrapy 数据重复爬取
爬分页时容易重复爬同一页,在start_urls生成时用range控制页数,或在parse方法里判断是否已爬过该 URL。 - 过度依赖高级函数
别为了用高级函数而用,比如简单的求和用sum()比agg('sum')更直观,适合的才是最好的。
五、自问自答:进阶学习常问的 3 个问题
- “Pandas 和 Scrapy 的高级用法这么多,该先学哪个?”
建议先巩固基础,再分方向学。数据分析岗先深钻 Pandas,爬虫岗重点攻 Scrapy,两者结合的场景(比如爬数后分析)可以最后练,循序渐进效果好。 - “没有企业数据,怎么练高级用法?”
网上有很多公开数据集,比如 Kaggle 的电商数据、政府公开数据,爬取练习可以找豆瓣、维基百科这些反爬宽松的网站,练熟了再挑战复杂网站。 - “学高级用法需要数学或计算机基础吗?”
不用太深,但懂点基础更好。比如 Pandas 的矢量化操作不用懂底层原理,会用就行;Scrapy 的中间件机制,大概知道 “拦截请求 / 响应” 的逻辑就能用,边用边学原理更轻松。
结尾心得
Pandas 和 Scrapy 的高级用法看似复杂,其实都是基础的延伸,关键是多练真实场景。兔子哥的经验是,遇到数据卡顿时就想 “有没有矢量化方法”,爬虫被拦时就试 “中间件加代理 / 随机头”,解决问题的过程就是进步的过程。别害怕报错,高级用法都是在一次次调试中学会的。建议每天练一个小案例,比如用 Pandas 处理一份报表,用 Scrapy 爬一个小网站,坚持一个月,你会发现处理复杂问题的能力明显提升,这才是进阶的真谛!
标签: stats.columns 数据分析
版权声明:除非特别标注,否则均为本站原创文章,转载时请以链接形式注明文章出处。
还木有评论哦,快来抢沙发吧~