
在使用 goquery 选择 html 元素时,若 class 属性包含空格(如 `class="text title"`),需理解其语义为**多个独立类名**;正确写法是用 `.text.title`(无空格、连续点号)匹配同时具有这两个类的元素,而非 `.text title`(后者表示后代选择器)。
HTML 规范明确规定:class 属性值是一个以空格分隔的类名列表。例如 表示该元素同时拥有 text 和 title 两个 CSS 类。因此,在 CSS 选择器(以及 goquery 所依赖的 CSS 选择器语法)中:
- .text.title 表示“同时具有 text 和 title 两个类”的元素(交集);
- .text title(中间有空格)则表示“在 .text 元素内部的 title 元素”(后代选择器),完全不是目标含义;
- .title 单独使用,则匹配所有含 title 类的元素(无论是否还含其他类)。
回到原始示例,以下代码可正确提取 Go :
doc.Find(".text.title").Each(func(i int, s *goquery.Selection) {
class, _ := s.Attr("class")
fmt.Printf("class=%q, text=%q\n", class, s.Text()) // 输出:class="text title", text="Go "
})⚠️ 注意事项:
- goquery.Find() 完全遵循标准 CSS 选择器语法,不支持正则或子字符串匹配(如无法直接匹配“class 属性中包含 text 字符串”的元素);
- 若需模糊匹配(例如查找 class 属性值中含有空格且包含 text 的元素),应改用 Filter() 配合自定义逻辑:
doc.Find("span").Filter(func(i int, s *goquery.Selection) bool { if class, exists := s.Attr("class"); exists { return strings.Contains(class, "text") && strings.Contains(class, " ") } return false }).Each(func(i int, s *goquery.Selection) { fmt.Println("Found span with space-containing class containing 'text':", s.Text()) }) - 实际项目中,优先采用语义清晰的多类名组合(如 .btn.btn-primary),避免依赖空格解析逻辑,提升可维护性与选择器可靠性。
总结:掌握 HTML class 属性的多值本质与 CSS 选择器的点号连接规则,是高效使用 goquery 的关键基础——空格是类名分隔符,不是类名的一部分;点号连接才是多类联合选择的正确语法。
立即学习“前端免费学习笔记(深入)”;











