当前位置: 首页 > article >正文

#去除知乎中“盐选”付费故事

添加油猴脚本,去除知乎中“盐选”付费故事

// ==UserScript==
// @name         盐选内容隐藏脚本
// @namespace    http://tampermonkey.net/
// @version      0.2
// @description  自动隐藏含有“盐选专栏”或“盐选”文字的回答卡片
// @author       YourName
// @match        *://*.zhihu.com/*
// @grant        none
// ==/UserScript==(function() {'use strict';// 配置const observerConfig = {childList: true,subtree: true,attributes: false};// 目标元素选择器和条件const targets = [{selector: 'div.KfeCollection-OrdinaryLabel-content',keyword: '盐选专栏'},{selector: 'p.KfeCollection-IntroCard-contentName-newStyle-pc',keyword: '盐选'}];const ancestorSelector = 'div.Card.TopstoryItem.TopstoryItem-isRecommend';// 隐藏卡片的通用函数const hideCard = (element) => {const ancestor = element.closest(ancestorSelector);if (ancestor) {ancestor.remove();}};// 检查节点并隐藏匹配的卡片const checkNode = (node) => {targets.forEach(target => {if (node.matches(target.selector) && node.textContent.includes(target.keyword)) {hideCard(node);}Array.from(node.querySelectorAll(target.selector)).forEach(element => {if (element.textContent.includes(target.keyword)) {hideCard(element);}});});};// 创建MutationObserver实例const observer = new MutationObserver(mutations => {mutations.forEach(mutation => {mutation.addedNodes.forEach(node => {if (node.nodeType === Node.ELEMENT_NODE) {checkNode(node);}});});});// 初始检查已存在的内容const initialCheck = () => {targets.forEach(target => {document.querySelectorAll(target.selector).forEach(element => {if (element.textContent.includes(target.keyword)) {hideCard(element);}});});};// 启动观察器observer.observe(document.documentElement, observerConfig);// 页面加载时执行初始检查window.addEventListener('load', initialCheck);
})();

二、附加解释

MutationObserver 是一个用于监听 DOM 树变化的 JavaScript API。它允许你实时检测网页中元素的变化(如添加、删除节点或属性修改),非常适合处理动态加载的内容,比如知乎页面中通过 AJAX 加载的推荐卡片。以下是对脚本中 MutationObserver 使用的详细解释:
  1. MutationObserver 的作用
    MutationObserver 提供了一种高效的方式来监听 DOM 变化,而无需轮询或依赖定时器。在你的脚本中,它用于检测知乎页面中新增的 DOM 节点(例如新加载的推荐卡片),并检查这些节点是否包含“盐选”相关内容,以便隐藏对应的卡片。
  2. 脚本中 MutationObserver 的使用
    以下是脚本中 MutationObserver 的具体实现和步骤:
    a. 创建 MutationObserver 实例
const observer = new MutationObserver(mutations => {mutations.forEach(mutation => {mutation.addedNodes.forEach(node => {if (node.nodeType === Node.ELEMENT_NODE) {checkNode(node);}});});
});

new MutationObserver(callback):创建一个观察者实例,callback 是一个函数,当 DOM 发生变化时会被调用。
回调函数:接收 mutations 参数(一个 MutationRecord 数组),每个 MutationRecord 描述一次 DOM 变化。
处理逻辑:
遍历 mutations 中的每个变化。
检查 mutation.addedNodes(新增的节点列表)。
只处理元素节点(node.nodeType === Node.ELEMENT_NODE),忽略文本节点等。
对每个新增元素调用 checkNode 函数,检查是否需要隐藏卡片。
b. 配置观察器

const observerConfig = {childList: true,subtree: true,attributes: false
};

observerConfig:定义观察器的监听范围和类型:
childList: true:监听目标节点及其子节点的添加或删除。
subtree: true:监听目标节点的所有后代节点(不仅是直接子节点)。
attributes: false:不监听属性变化(因为脚本只关心节点增删)。
这种配置确保脚本能捕捉页面中任何位置的新增节点(如动态加载的推荐卡片)。
c. 启动观察

observer.observe(document.documentElement, observerConfig);

observer.observe(target, config):开始观察指定的目标节点。
目标节点:document.documentElement(即 元素),覆盖整个页面。
配置:使用 observerConfig,监听整个 DOM 树的节点变化。
3. 为什么使用 MutationObserver
知乎页面是动态加载的,推荐卡片可能在页面滚动或刷新时通过 JavaScript 插入 DOM。如果只在页面加载时检查(initialCheck),会漏掉后续加载的内容。MutationObserver 的优势在于:
实时性:它能立即响应 DOM 变化,无需手动轮询。
高效性:相比定时器(如 setInterval),它只在 DOM 实际变化时触发,性能更好。
全面性:通过 subtree: true,可以监控整个页面,包括深层嵌套的动态内容。
4. 脚本中 MutationObserver 的工作流程
初始化:
创建 MutationObserver 实例,定义当 DOM 变化时检查新增节点的逻辑。
配置为监听整个 DOM 树的节点增删。
启动:
开始观察 元素,监控页面中任何新增节点。
处理变化:
当页面加载新内容(例如滚动时插入新卡片),MutationObserver 检测到 addedNodes。
对每个新增元素节点调用 checkNode,检查是否匹配目标选择器(div.KfeCollection-OrdinaryLabel-content 或 p.KfeCollection-IntroCard-contentName-newStyle-pc)和关键字(“盐选专栏”或“盐选”)。
如果匹配,找到祖先卡片(div.Card.TopstoryItem.TopstoryItem-isRecommend)并移除。
初始检查补充:
由于 MutationObserver 只监听变化,脚本还通过 window.addEventListener(‘load’, initialCheck) 检查页面加载时已存在的卡片。
5. 代码中的优化点
节点类型检查:脚本通过 node.nodeType === Node.ELEMENT_NODE 过滤非元素节点(如文本节点),提高效率。
选择器检查:checkNode 使用 matches 和 querySelectorAll,确保只处理符合条件的元素。
去重逻辑:通过 hideCard 函数统一卡片移除逻辑,避免重复代码。
6. 可能的改进
性能优化:如果页面变化频繁,可以限制观察范围(例如只观察某个容器如 div.Topstory-container),减少不必要的检查。
断开观察:在某些场景下(例如页面切换),可以通过 observer.disconnect() 停止观察以释放资源。
错误处理:添加 try-catch 块处理 DOM 操作中的潜在异常。
7. 总结
MutationObserver 在脚本中用于实时监控知乎页面中的 DOM 变化,捕获动态加载的推荐卡片,并检查是否包含“盐选”相关内容。通过配置 childList 和 subtree,它能高效地覆盖整个页面,确保新插入的卡片被及时处理。结合初始检查,脚本实现了对静态和动态内容的全面覆盖,完美适配知乎的动态加载场景。

相关文章:

#去除知乎中“盐选”付费故事

添加油猴脚本,去除知乎中“盐选”付费故事 // UserScript // name 盐选内容隐藏脚本 // namespace http://tampermonkey.net/ // version 0.2 // description 自动隐藏含有“盐选专栏”或“盐选”文字的回答卡片 // author YourName // mat…...

MATLAB脚本实现了一个转子系统的参数扫描和分岔分析

% 参数扫描范围 clc; clear; close all;S_values 500:200:20000; % 转速范围% 定义系统参数 N 5; % 质量点数量 num_nodes N; % 节点数 num_dofs_per_node 4; % 每个节点的自由度数 num_elements num_nodes-1; % 单元数 total_dofs num_nodes * num_dofs_per_node; % 总自…...

UWP发展历程

通用Windows平台(UWP)发展历程 引言 通用Windows平台(Universal Windows Platform, UWP)是微软为实现"一次编写,处处运行"的愿景而打造的现代应用程序平台。作为微软统一Windows生态系统的核心战略组成部分,UWP代表了从传统Win32应用向现代应…...

数据库相关概念,关系型数据库的核心要素,MySQL(特点,安装,环境变量配置,启动,停止,客户端连接),数据模型

目录 数据库相关概念 MySQL(特点,安装,环境变量配置,启动和停止,客户端连接) MySQL数据库的特点 Windows下安装MySQL MySQL 8.0.36(安装版) MySQL安装 配置Path环境变量 MySQ…...

Facebook隐私保护:从技术到伦理的探索

在这个数字化时代,隐私保护已成为公众关注的焦点。Facebook,作为全球最大的社交媒体平台之一,其用户隐私保护问题更是引起了广泛的讨论。本文将从技术层面和伦理层面探讨 Facebook 在隐私保护方面的努力和挑战。 技术层面的隐私保护 在技术…...

三维点拟合平面ransac c++

理论 平面的一般定义 在三维空间中,一个平面可以由两个要素唯一确定: 法向量 n(a,b,c):垂直于平面的方向 平面上一点 平面上任意一点 p(x,y,z) 满足: ( p − p 0 ) ∗ n 0 (p - p0) * n 0 (p−p0)∗n0 即 a ( x − x 0 ) …...

香港服务器CPU对比:Intel E3与E5系列核心区别与使用场景

香港服务器的 CPU 配置(核心数与主频)直接决定了其并发处理能力和数据运算效率,例如高频多核处理器可显著提升多线程任务响应速度。在实际业务场景中,不同负载需求对 CPU 架构的要求存在显著差异——以 Intel E3 和 E5 系列为例,由于两者在性…...

ChatGPT-o3辅助学术大纲效果如何?

目录 1 引言 2 背景综述 2.1 自动驾驶雷达感知 2.2 生成模型演进:从 GAN 到 Diffusion 3 相关工作 3.1 雷达点云增强与超分辨率 3.2 扩散模型在数据增广中的应用 4 方法论 4.1 问题定义与总览 4.2 数据预处理与雷达→体素表示 4.3 潜在体素扩散网络&…...

AI大模型API文档的核心内容概述,以通用框架和典型实现为例

以下是AI大模型API文档的核心内容概述,以通用框架和典型实现为例: 一、API基础架构 1. 基础信息 API类型:RESTful API或gRPC(如阿里云通义千问支持HTTPS接口)请求方式:通常为POST方法基础URL&#xff1a…...

使用pnpm第一次运行项目报错 ERR_PNPM_NO_PKG_MANIFEST No package.json found in E:\

开始用unibestpnpm写一个小程序 运行pnpm init报错 如标题所示没有package.json这个文件 博主犯了一个很愚蠢的错误。。 准备方案手动创建一个json文件 此时才发现没到根目录下,创建了一个项目之后就没有切入文件夹里。 切入根目录再下载就成功啦...

单线服务器有什么优点

单线服务器是一个普遍存在的术语,它是指一种服务器连接互联网时只使用一个物理线路的服务器。简单来说,就是使用一条网络线路的服务器,上传和下载的数据都通过一个通道实现。在当今数字化的时代,服务器的选择至关重要。今天&#…...

手持式三维扫描设备赋能智能汽车制造

随着电动化与智能化趋势的加速,传统逆向工程手段已难以满足复杂零部件的建模需求。 ‌3D逆向建模‌技术,为汽车制造企业提供高效、精准的数字化解决方案。 传统汽车零部件的尺寸检测与建模依赖三坐标测量机(CMM)或人工测绘&#…...

FA-YOLO:基于FMDS与AGMF的高效目标检测算法解析

本文《FA-YOLO: Research On Efficient Feature Selection YOLO Improved Algorithm Based On FMDS and AGMF Modules》针对YOLO系列在特征融合与动态调整上的不足,提出两种创新模块:​FMDS(细粒度多尺度动态选择模块)​和AGMF(自适应门控多分支聚焦融合模块)​。论文结构…...

Hutool之DateUtil:让Java日期处理变得更加简单

前言 在Java开发中,日期和时间的处理是一个常见问题。为了简化这个过程,许多开发者会使用第三方工具包,如Hutool。Hutool是一个Java工具包,提供了许多实用的功能,其中之一就是日期处理。日期时间工具类是Hutool的核心包…...

Ambari 中移除/重装 yarn 集群中的 NodeManager 节点

文章目录 背景分析解决分析:现有 NodeManager 情况移除:240 服务器上的 NodeManager重新安装:240 服务器上的安装 NodeManager疑问为什么直接添加就可以运行?参考背景 项目中有Spark应用,主要在 yarn 集群中部署。 现在发现 yarn 集群中的节点资源过剩,需要将部分节点移…...

小程序在 skyline 下如何开启多行省略

参考:https://developers.weixin.qq.com/community/develop/doc/000a648baacca06e83f1034d66c000 前言 小程序在 skyline 下不支持 line-clamp,想要开启多行省略使用 text 组件的 max-lines 结合 overflow 属性。 解决办法:skyline 下不支…...

uni.createInnerAudioContext踩坑duration在真机环境一直为0

解决 uni.createInnerAudioContext 的 duration 在真机环境一直为 0 的问题 在使用 uni.createInnerAudioContext 播放音频时,开发者可能会遇到以下问题: duration 在真机环境中一直为 0:即使音频文件是正常的,duration 属性也无法正确获取音频的时长。音频实例未放到全局…...

《MySQL:MySQL数据类型分类》

数据类型分类 数值类 tinyint类型 数值越界测试。 在MySQL中,整型可以指定是有符号的和无符号的,默认是有符号的。 可以通过UNSIGNED来说明某个字段是无符号的。 无符号整型数值越界测试。 如果我们向mysql特定的类型中插入不合法的数据,my…...

Kubernetes》》k8s》》Namespace

Namespace 概述 Namespace(命名空间) 是 Kubernetes 中用于逻辑隔离集群资源的机制,可将同一集群划分为多个虚拟环境,适用于多团队、多项目或多环境(如开发、测试、生产)的场景。 核心作用: 资…...

ZYNQ笔记(八):UART 串口中断

版本:Vivado2020.2(Vitis) 任务:UART串口中断实验,实现串口中断数据回环(接收数据并发送出去) 目录 一、介绍 二、硬件设计 三、软件设计 四、效果 一、介绍 ZYNQ 的 UART(Unive…...

vue3 nprogress 使用

nprogress 介绍与作用 1.nprogress 是一个轻量级的进度条组件,主要用于在页面加载或路由切换时显示一个进度条,提升用户体验。它的原理是通过在页面顶部创建一个 div,并使用 fixed 定位来实现进度条的效果 2.在 Vite Vue 3 项目中&#xf…...

相比其他缓存/内存数据库(如 Memcached, Ehcache 等),Redis 在微服务环境中的优势和劣势是什么?

我们来比较一下 Redis 与 Memcached、Hazelcast、Ehcache 等在微服务环境下的优势和劣势。 Redis 的优势 : 丰富的数据结构 (Rich Data Structures): 优势: 这是 Redis 最显著的优势之一。除了简单的 Key-Value (字符串) 外,Redis 还原生支持 Lists, Sets, Sorted …...

生态篇|多总线融合与网关设计

引言 1. 车内多总线概览 2. 主流车载总线技术对比 3. 网关设计原则与架构 4. 协议转换与映射策略 5. 安全与诊断功能集成...

Node做BFF中间层架构优化前端开发体验并提升系统整体性能。

文章目录 1. BFF 层的定位2. 技术选型3. 架构设计3.1 分层设计3.2 示例架构 4. 核心功能实现4.1 数据聚合4.2 权限校验4.3 缓存优化 5、实战示例1. 场景说明2. ECharts 数据格式要求3. BFF 层实现步骤3.1 接收前端参数3.2 调用后端服务获取数据 4. 前端使用 总结 在使用 Node.j…...

基于autoware1.14的实车部署激光雷达循迹,从建图、定位、录制轨迹巡航点、到实车运行。

1.首先安装autoware ,大家可以以下一下博客进行安装,如果缺少库什么的直接问ai安装对应的库就行。ubuntu18.04安装Autoware1.14---GPU版 最全环境配置说明_autoware1.14安装教程-CSDN博客 安装成功后运行: source install/setup.bash roslau…...

数据类型相关问题导致的索引失效 | OceanBase SQL 优化实践

背景 针对在OceanBase 论坛中遇到的一些典型SQL调优问题,进行记录与总结,分享给大家。本文介绍的事3个场景:数据类型不匹配、字符集相关属性不匹配,和过滤/联接条件上包含系统函数。 场景一:数据类型不匹配 类型不匹…...

云计算(Cloud Computing)概述——从AWS开始

李升伟 编译 无需正式介绍亚马逊网络服务(Amazon Web Services,简称AWS)。作为行业领先的云服务提供商,AWS为全球开发者提供了超过170项随时可用的服务。 例如,Adobe能够独立于IT团队开发和更新软件。通过AWS的服务&…...

UE学习记录part18

225 animation blueprint templates: generic animation blueprints 在Animation Blueprint中选择template生成动画蓝图模板 在function中选择blurprintthreadsafeupdateanimation,用于做数据的更新 先创建变量,再将变量再blueprintinitializeanimation…...

刀片服务器的散热构造方式

刀片服务器的散热构造是其高密度、高性能设计的核心挑战之一。其散热系统需在有限空间内高效处理多个刀片模块产生的集中热量,同时兼顾能耗、噪音和可靠性。以下从模块化架构、核心散热技术、典型方案对比、厂商差异及未来趋势等方面展开分析: 一、模块化散热架构 刀片服务器…...

算法01-最小生成树prim算法

最小生成树prim算法 题源:代码随想录卡哥的题 链接:https://kamacoder.com/problempage.php?pid1053 时间:2025-04-18 难度:4⭐ 题目: 1. 题目描述: 在世界的某个区域,有一些分散的神秘岛屿&…...