XPath提取@href/@src返回空的根本原因是HTML解析失败或命名空间干扰;应优先用lxml.html解析,处理SVG需注册xlink命名空间,并注意懒加载属性如data-src。

用 xpath 提取 @href 和 @src 时,为什么返回空?
常见现象是:元素明明在页面里,xpath 表达式也看着对,但 tree.xpath("//a/@href") 却返回空列表。根本原因通常是 HTML 解析失败或命名空间干扰——lxml 默认按 XML 规则解析,而真实网页常含不规范标签、自闭合写法(如 <img src="x"> 被误判为未闭合),或混有 SVG/HTML5 自定义属性。
实操建议:
立即学习“Python免费学习笔记(深入)”;
- 优先用
html.parser或lxml.html替代原生lxml.etree,例如:from lxml import html; tree = html.fromstring(html_content) - 避免直接用
etree.parse()读 HTML 文件,它会严格校验结构,容易崩 - 若网页含内联 SVG,
@href可能在http://www.w3.org/1999/xlink命名空间下,此时需显式注册前缀:tree.xpath('//svg:a/@xlink:href', namespaces={'xlink': 'http://www.w3.org/1999/xlink'})
tree.xpath() 中 @href 和 @src 的路径写法差异
看似都是取属性,但实际写法受目标标签语义和 DOM 层级影响极大。不是所有链接都藏在 <a> 里,也不是所有图片地址都在 <img src> 中——现代页面大量使用 <source>、<iframe>、data-src 等变体。
实操建议:
立即学习“Python免费学习笔记(深入)”;
- 提取超链接优先用:
tree.xpath('//a[@href]/@href')(加[@href]过滤掉无值节点,避免空字符串) - 提取图片地址别只盯
<img>,顺手补上:tree.xpath('//img[@src]/@src | //img[@data-src]/@data-src | //source[@srcset]/@srcset') - 注意相对 URL:返回的
@href值可能是/login或./assets/logo.png,后续需用urllib.parse.urljoin(base_url, href)拼成绝对地址
用 xpath 提取属性时,text_content() 和 get() 谁更稳?
这是新手常混淆的点:xpath 返回的是字符串列表,而 Element.get("href") 是单个元素的方法。二者适用场景完全不同——前者适合批量提取,后者适合已定位到具体节点后安全取值。
实操建议:
立即学习“Python免费学习笔记(深入)”;
- 批量提取属性,坚持用
xpath:它天然支持多路径合并、条件过滤,比如tree.xpath('//a[contains(@class,"btn")]/@href') - 若已用
tree.xpath("//a")[0]定位到某元素,再取属性请用.get("href"),比.xpath("@href")[0]更快且不抛异常(.get()返回None,而xpath空列表索引会报IndexError) - 警惕
get()对布尔属性(如disabled、checked)的返回值:存在即返回""(空字符串),不是"true"
为什么用 xpath 提取 @src 时,懒加载图片总拿不到真实地址?
因为懒加载图片的 @src 常被设为占位图(如 data:image/gif;base64,R0l...),真实地址藏在 @data-src、@data-lazy-src 甚至 @srcset 里。XPath 不会自动识别“懒加载意图”,它只认字面属性名。
实操建议:
立即学习“Python免费学习笔记(深入)”;
- 先检查目标元素的全部属性:
elem.attrib(elem是xpath返回的 Element 对象),确认真实地址字段名 - 写 XPath 时用
|合并多个可能属性:tree.xpath('//img[@data-src]/@data-src | //img[@data-lazy]/@data-lazy | //img[@srcset]/@srcset') - 若
@srcset值含多个分辨率(如"small.jpg 480w, big.jpg 1024w"),需额外用正则提取主地址,XPath 本身不支持字符串切分
真正麻烦的不是语法,而是网页作者怎么写 markup —— 同一个“图片地址”,可能今天叫 data-src,明天改成 data-image-url,XPath 得跟着变。没有银弹,只有现场看源码、试表达式、加容错。










