Skip to content

Latest commit

 

History

History
382 lines (265 loc) · 7.94 KB

561-194109-xpath_属性筛选_attrib_属性字典.sy.md

File metadata and controls

382 lines (265 loc) · 7.94 KB
show version enable_checker
step
1.0
true

语法 html 生成

回忆

  • 上次深入了 xpath
  • xpath
    • 用来筛选
    • xml 文件中的节点
表达式 描述
nodename 在当前位置选择此类节点
/ 从根节点选取 或 表示层级关系
// 在任意层级下的子孙路径下
. 选取当前节点
.. 选取当前节点的父节点
@ 选取属性
  • @选属性 这个
    • 我们还没有试
    • 怎么用呢?🤔

直接搜索元素

  • l_et_前缀代表着
    • 这是 元素树节点的列表
    • list of element tree
import requests
from lxml import etree
response = requests.get("http://localhost")
b_html = response.content
print(b_html)
et_html = etree.HTML(b_html)
l_et_element = et_html.xpath("//a")
for element in l_et_element:
	print(element)
  • 任意层级下的
    • a元素

图片描述

  • 找到
    • 2个a元素

图片描述

根据属性类型筛选

  • //a[@href]
    • //a
      • 任意层级下的
      • a元素
    • [@href]
      • 有@href属性的

图片描述

  • 任意路径下
    • 有href属性的
    • a元素

图片描述

  • 这里 用到的 中括号
    • 叫什么 方法 呢?

谓语 predicates

  • 谓词 predicates

图片描述

  • 如何理解谓词呢?

图片描述

  • 谓词
    • 是 对元素 进一步的描述
    • 是 筛选元素的 方式

根据属性值筛选

  • 中括号叫做谓词

图片描述

图片描述

  • 注意 属性值 引用
    • 单引号或者双引号都可以
    • 冲突了的话 需要转义

谓词筛选

  • 根据是否有属性
    • 筛选元素
  • //a[@*]
    • //a
      • 任意层级下的
      • a元素
    • [@*]
      • []是筛选谓词
      • @是attribute
      • *是任意的
      • 有任意属性的

图片描述

  • 任意层级下
    • 有任意属性的
    • a元素

图片描述

  • 可以 按位置 筛选 吗?

双重谓词

  • 任意层级下的
    • 位置小于2的
    • 有href的a元素

图片描述

  • 以下xpath等价
表达式 描述
//a[postion()<2] 任意层级下 位置小于2的 a元素
//a[postion()=1] 任意层级下 位置等于1的 a元素
//a[1] 任意层级下 第一个 a元素

图片描述

  • xpath 可以
    • 成功得到元素列表
  • 但是
    • 可以得到 元素的属性 吗?

观察网页

图片描述

  • 这次尝试
    • 筛选属性
    • a 元素 下的
    • href 属性
import requests
from lxml import etree
response = requests.get("http://localhost")
b_html = response.content
print(b_html)
et_html = etree.HTML(b_html)
l_attrib = et_html.xpath("//a/@href")
print(l_attrib)
  • 任意层级下的
    • a元素的
    • href属性

xpath

  • 得到属性的列表

图片描述

  • 任意路径下
    • a元素的
    • href属性

图片描述

  • 得到一个
    • 属性值的列表
  • 如果
    • 不筛选a元素呢?

href

  • 修改

图片描述

  • 任意路径下
    • 任意元素的
    • href属性

图片描述

  • 目前可以筛选到属性值
    • 可以根据元素 同时得到
    • 属性名 和 属性值 吗?

属性变量

import requests
from lxml import etree
response = requests.get("http://localhost/food.html")
b_html = response.content
et_html = etree.HTML(b_html)
et_html.
  • 到游乐场找找

图片描述

  • attrib 就是属性
    • 具体什么类型呢?

查看类型

et_html
et_html.attrib
  • 类型 好像是 字典

图片描述

  • 尝试遍历

遍历过程

  • "//*[@*]"
    • // 任意层级下的
    • * 任意元素
    • [@*] 需要拥有任意属性
import requests
from lxml import etree
response = requests.get("http://localhost")
b_html = response.content
et_html = etree.HTML(b_html)
l_e = et_html.xpath("//*[@*]")
for element in l_e:
    print(element.attrib)
  • 找到 任意层级下
    • 所有 有属性的元素
    • 打印他的属性字典

图片描述

  • 可以按照字典的方式
    • 输出attrib吗?

输出

import requests
from lxml import etree
response = requests.get("http://localhost")
b_html = response.content
et_html = etree.HTML(b_html)
l_e = et_html.xpath("//*[@*]")
for element in l_e:
    print(element.tag)
    for key, value in element.attrib.items():
        print(key,value,sep=":")
  • 输出结果

图片描述

  • 我们再温习一下下

尝试

  • 这里面出现了索引运算符[]
  • 找一下/html/body下
    • 第 1 个 p

图片描述

最后一个

  • /html/body/
    • 最后一个p元素

图片描述

  • 在索引运算符中使用了 last()
    • 此时last() = 3

倒数第二

  • 倒数第二个p

图片描述

  • 关键还是对 li 使用索引运算符
    • last()是最后一个
    • last() - 1 是倒数第二个

前两名 position

  • 前两个p

图片描述

  • p[position()<3]
    • 可以找到前两项
  • 如果我想找后两项呢?🤔

后两项

图片描述

  • p[position()>last()-2]
  • 可以找到后两项

存在href属性的a元素

  • 拥有href属性 的 a元素 🤪

图片描述

  • 可以试试href属性是特定值吗?

属性内容

图片描述

总结

  • 这次深入了 xpath 的筛选
    • 可以用中括号索引的方式对于子元素的位置进行筛选
xpath 表达式 含义
xpath("//p[1]") 第一个p
xpath("//p[last()]") 最后一个p
xpath("//p[position()<=3]") 正数前三个p
xpath("//p[position()>last()-2"]) 倒数两个p
  • 可以在索引中对属性进行筛选
    • @ 俗称花 a
    • 对应@ttribute
xpath 表达式 含义
//*[@href] 任意层级下
有href属性的
元素
//*[@href=\"http://nginx.org/"] 任意层级下
href属性是特定值的
元素
//a[last()][@href=\"http://nginx.org/"] 任意层级下
href属性是特定值的
最后一个
元素
//@ 任意层级下
任意属性
  • 还有什么好玩的呢?🤔
  • 下次再说