FPGA通过I2C控制AT24C64
文章目录
- 前言
- 一、代码设计框图
- 二、IIC_drive模块设计
- 2.1、模块接口:
- 2.2、代码功能描述:
- 2.3、IIC协议实现过程:
- 三、EEPROM_ctrl模块设计
- 3.1、模块接口:
- 3.2、代码功能描述
- 四、EEPROM_drive模块
- 五、iic_top模块
前言
继上一篇FPGA学习_I2C总线协议内容,本文将基于FPGA通过I2C控制AT24C64(EEPROM芯片)芯片。
AT24C64:256pages 32bitbyte each pages,存储大小为32 * 256 * 8 = 64Kb = 8KB
一、代码设计框图

完整代码GitHub连接:https://github.com/shun6-6/IIC_EEPROM_Pro
二、IIC_drive模块设计
参考FPGA奇哥系列网课
2.1、模块接口:
module iic_drive#(parameter P_ADDR_WIDTH = 16
)(input i_clk ,input i_rst ,/*----user interface----*/input [6 :0] i_device_addr ,//用户输入设备地址input [15:0] i_operation_addr ,//用户输入读写数据地址input [7 :0] i_operation_len ,//用户输入读写数据长度input [1 :0] i_operation_type ,//用户输入读写类型input i_operation_valid ,//用户输入操作有效信号output o_operation_ready ,//用户输出操作准备信号input [7 :0] i_write_date ,//用户写入数据output o_write_req ,//用户写数据请求output [7 :0] o_read_date ,//输出IIC读到的数据output o_read_valid ,//数据有效信号/*----IIC interface----*/output o_iic_scl ,//IIC时钟线inout io_iic_sda //IIC双向数据线
);
2.2、代码功能描述:
该模块将输入的指令以及相关地址和数据通过IIC协议传递给EEPROM芯片,其中状态机一共有11个状态:
localparam P_ST_IDLE = 0 ,//状态机-空闲P_ST_START = 1 ,//状态机-起始位P_ST_UADDR = 2 ,//状态机-设备地址P_ST_DADDR1 = 3 ,//状态机-数据地址高位P_ST_DADDR2 = 4 ,//状态机-数据地址低位P_ST_WRITE = 5 ,//状态机-写数据P_ST_REATART = 6 ,//状态机-重启iic总线P_ST_READ = 7 ,//状态机-读数据P_ST_WATI = 8 ,//等待应答后再发生停止位P_ST_STOP = 9 ,//状态机-停止P_ST_EMPTY = 10 ;//空状态
状态转移过程:
P_ST_IDLE :一次操作指令握手成功后,进入START状态;
P_ST_START :该状态下控制SCL和SDA线启动IIC,随后进入写设备地址UADDR状态,
P_ST_UADDR :w_st_turn 信号表示一个byte写入结束,即设备地址和读写指令写入(俩个一共为8bit)结束,随后会判断r_st_restart 信号,该信号表示当前操作为读数据操作,因为只有在读数据时,我们采用随机地址读操作,有一次虚写操作,虚写结束后需要重新启动总线,因此若此信号为高需要进入READ读阶段,否则进入写数据地址1(P_ST_DADDR1)阶段;
P_ST_DADDR1 :r_slave_ack 信号表示从机响应信号,此时响应的是写设备地址阶段的响应信号,如果响应为0,即未响应,则直接进入STOP停止阶段,以重新启动总线,这是由于刚刚写完数据,如果立马进行操作总线,总线处于忙状态,不会响应,若正常响应,则会在顺利写完8bit数据后进入P_ST_DADDR2 阶段。
P_ST_DADDR2 :在写完8bit的低8为地址后(即w_st_turn 拉高),判断当前是读操作还是写操作,写操作则顺利进入写数据WRITE阶段,读操作则需要进入总线重新启动阶段,即P_ST_REATART 。
P_ST_WRITE :当写如byte字节数与用户输入的写数据长度一致时,进入等待WAIT状态,否则继续写;
P_ST_REATART :重启总线,先进入停止STOP阶段,执行停止操作。
P_ST_READ :字节读,此模块只支持字节读操作,但用户要实现多字节读操作也是可以的,该过程会在EEPROM_drive当中被实现,因为EEPROM_drive模块会执行多次字节读。以此实现连续读操作。
P_ST_WATI :等待一拍,等从机ACK结束后进入停止位STOP阶段。

P_ST_STOP :控制SCL和SDA线结束IIC操作
注:这里需要注意的是接收完ACK后,不可以直接停止时钟产生,然后直接拉高SDA,需要多产生一个周期SCL,然后在SCL高电平期间拉高SDA以产生停止信号。
P_ST_EMPTY :emmmmm没啥用的一个状态,完全可以将停止位多计数一个时钟执行响应的判断,不过这样写清晰一点,主要是判断是不是需要重启总线(r_st_restart说明是由于读操作导致的重启操作,r_ack_lock说明是由于从机忙没有回应导致的重启总线),如果是则进入START状态,不是就回到IDLE状态。
always @(*)begincase (r_st_cur)P_ST_IDLE : r_st_nxt = w_operation_active ? P_ST_START : P_ST_IDLE;P_ST_START : r_st_nxt = P_ST_UADDR;P_ST_UADDR : r_st_nxt = w_st_turn ? r_st_restart ? P_ST_READ : P_ST_DADDR1: P_ST_UADDR;P_ST_DADDR1 : r_st_nxt = r_slave_ack ? P_ST_STOP : w_st_turn ? P_ST_DADDR2 : P_ST_DADDR1;P_ST_DADDR2 : r_st_nxt = w_st_turn && ri_operation_type == P_W ? P_ST_WRITE : w_st_turn && ri_operation_type == P_R ? P_ST_REATART :P_ST_DADDR2;P_ST_WRITE : r_st_nxt = w_st_turn && r_wr_cnt == ri_operation_len - 1 ? P_ST_WATI : P_ST_WRITE;P_ST_REATART : r_st_nxt = P_ST_STOP;P_ST_READ : r_st_nxt = w_st_turn ? P_ST_WATI : P_ST_READ;//随机读,一次一个byteP_ST_WATI : r_st_nxt = P_ST_STOP;P_ST_STOP : r_st_nxt = r_st_cnt == 1 ? P_ST_EMPTY : P_ST_STOP;P_ST_EMPTY : r_st_nxt = r_st_restart | r_ack_lock ? P_ST_START : P_ST_IDLE;default : r_st_nxt = P_ST_IDLE;endcase
end
2.3、IIC协议实现过程:
过程和之前介绍的SPI总线协议类似,通过维护一个计数器,来使数据在SCL时钟下降沿改变,在SCL时钟上升沿被采样

主要难点是停止位的部分:
- 写数据结束的停止位在第一张波形图哪里做了详细说明:
- 读数据结束的停止位:如下图所示:在黄线部分已经读完了数据,后面需要加一个时钟周期传输NO ACK(图中红线部分)表示此次字节读结束,然后停止位的产生一定还需要多一个时钟周期,并且在此时钟周期最后拉高SDA,其实和写数据停止位一样,重复说明防止出错!!!

三、EEPROM_ctrl模块设计
3.1、模块接口:
module eeprom_ctrl(input i_clk ,input i_rst ,/*----user interface----*/input [2 :0] i_eeprom_addr ,input [15:0] i_user_operation_addr ,input [1 :0] i_user_operation_type ,input [7 :0] i_user_operation_len ,input i_user_operation_valid ,output o_user_operation_ready ,input [7 :0] i_user_write_date ,input i_user_write_valid ,input i_user_write_sop ,input i_user_write_eop ,output [7 :0] o_user_read_date ,output o_user_read_valid ,/*----iic drive interface----*/output [6 :0] o_device_addr ,output [15:0] o_operation_addr ,output [7 :0] o_operation_len ,output [1 :0] o_operation_type ,output o_operation_valid ,input i_operation_ready ,output [7 :0] o_write_date ,input i_write_req ,input [7 :0] i_read_date ,input i_read_valid
);
3.2、代码功能描述
该模块主要讲用户输入的读写指令转化为驱动读写指令,并且将用户输入的写数据存入FIFO,一个一个把8bit数据吐给IIC驱动,因为IIC_drive是串行传输的,同时也把从EEPROM读出的数据暂存入FIFO,读完后一次性连续的传递给用户模块。同时在该模块当中完成了一个上面刚刚提到的操作,连续读 :IIC_drive模块只支持字节读操作,但用户要实现多字节读操作也是可以的,因为EEPROM_drive模块会执行多次字节读。以此实现连续读操作。
localparam P_ST_IDLE = 0 ,P_ST_WRITE = 1 ,P_ST_WAIT = 2 ,P_ST_READ = 3 ,P_ST_REREAD = 4 ,P_ST_OUT_DATA = 5 ;
always @(*)begincase (r_st_cur)P_ST_IDLE : r_st_nxt = w_user_active && i_user_operation_type == P_W ? P_ST_WRITE :w_user_active && i_user_operation_type == P_R ? P_ST_WAIT :P_ST_IDLE;P_ST_WRITE : r_st_nxt = w_drive_end && ri_user_operation_type == P_W ? P_ST_IDLE : P_ST_WRITE;P_ST_WAIT : r_st_nxt = P_ST_READ;P_ST_READ : r_st_nxt = w_drive_end ? r_read_cnt == ri_user_operation_len - 1 ? P_ST_OUT_DATA : P_ST_REREAD: P_ST_READ; P_ST_REREAD : r_st_nxt = P_ST_READ; P_ST_OUT_DATA : r_st_nxt = w_fifo_read_empty ? P_ST_IDLE : P_ST_OUT_DATA;default : r_st_nxt = P_ST_IDLE;endcase
end
该模块状态机以及相应跳转条件
该功能较为简单,
P_ST_IDLE :根据输入操作类型分别进入写WRITE状态或者是等待WAIT状态,这是因为用户输入的操作指令都会在本地先打一拍然后寄存下来,对于写数据而言,会先将数据存入FIFO然后再进行握手操作,然后再把本地寄存的用户指令再发给IIC驱动,这期间因为FIFO存数据所以指令赋值推后了好多拍,因此指令赋值不会出错,但是进行读数据操作时,用户指令i_user_operation_type先赋值给ri_user_operation_type以寄存,然后将ri_user_operation_type赋值给驱动ro_operation_type,在这个过程中就需要先等待一拍,否则就会出现上一次操作的的ri_user_operation_type给了ro_operation_type,错过了本次正确的i_user_operation_type。 这就是为什么进入读操作时先要进入一次WAIT状态以打一排。
之后的状态都很简单了!!!
四、EEPROM_drive模块
该模块就是例化了上述俩个模块
五、iic_top模块
该模块则是简单实现了一个不断翻转读写状态的的用户模块。
module iic_top(input i_clk ,output o_iic_scl ,//IIC时钟线inout io_iic_sda //IIC双向数据线);
localparam P_WRITE_NUM = 8;
localparam P_W = 1 ,//写数据P_R = 2 ;//读数据
reg [2 :0] ri_eeprom_addr ;
reg [15:0] ri_user_operation_addr ;
reg [1 :0] ri_user_operation_type ;
reg [7 :0] ri_user_operation_len ;
reg ri_user_operation_valid ;
wire o_user_operation_ready ;
reg [7 :0] ri_user_write_date ;
reg ri_user_write_valid ;
reg ri_user_write_sop ;
reg ri_user_write_eop ;
wire [7 :0] o_user_read_date ;
wire o_user_read_valid ;
reg [7 :0] r_write_cnt ;
reg r_wr_st ;
wire w_user_active ;
wire w_clk_5mhz ;
wire w_clk_5mhz_lock ;
wire w_clk_125khz ;
wire w_clk_125khz_rst ;
assign w_user_active = ri_user_operation_valid & o_user_operation_ready;
SYSCLK_div SYSCLK_div_5mhz(.clk_out1 (w_clk_5mhz ), .locked (w_clk_5mhz_lock), .clk_in1 (i_clk )
);
CLK_DIV_module#(.P_CLK_DIV_CNT (40) //MAX = 65535
)CLK_DIV_module_U(.i_clk (w_clk_5mhz ),.i_rst (~w_clk_5mhz_lock),.o_clk_div (w_clk_125khz ));
rst_gen_module#(.P_RST_CYCLE (1)
)rst_gen_module_u0( .i_clk (w_clk_125khz ),.o_rst (w_clk_125khz_rst));
eeprom_drive eeprom_drive_u0(.i_clk (w_clk_125khz ),.i_rst (w_clk_125khz_rst),.i_eeprom_addr (ri_eeprom_addr ),.i_user_operation_addr (ri_user_operation_addr ),.i_user_operation_type (ri_user_operation_type ),.i_user_operation_len (ri_user_operation_len ),.i_user_operation_valid (ri_user_operation_valid),.o_user_operation_ready (o_user_operation_ready ),.i_user_write_date (ri_user_write_date ),.i_user_write_valid (ri_user_write_valid ),.i_user_write_sop (ri_user_write_sop ),.i_user_write_eop (ri_user_write_eop ),.o_user_read_date (o_user_read_date ),.o_user_read_valid (o_user_read_valid ),.o_iic_scl (o_iic_scl ),//IIC时钟线.io_iic_sda (io_iic_sda) //IIC双向数据线);
always @(posedge w_clk_125khz or posedge w_clk_125khz_rst)beginif(w_clk_125khz_rst)beginri_eeprom_addr <= 'd0;ri_user_operation_addr <= 'd0;ri_user_operation_type <= 'd0;ri_user_operation_len <= 'd0;ri_user_operation_valid <= 'd0;endelse if(o_user_operation_ready && r_wr_st == 0)beginri_eeprom_addr <= 3'b011;ri_user_operation_addr <= 'd0;ri_user_operation_type <= P_W;ri_user_operation_len <= P_WRITE_NUM;ri_user_operation_valid <= 'd1;endelse if(o_user_operation_ready && r_wr_st == 1)beginri_eeprom_addr <= 3'b011;ri_user_operation_addr <= 'd0;ri_user_operation_type <= P_R;ri_user_operation_len <= P_WRITE_NUM;ri_user_operation_valid <= 'd1;endelse beginri_eeprom_addr <= 'd0;ri_user_operation_addr <= 'd0;ri_user_operation_type <= 'd0;ri_user_operation_len <= 'd0;ri_user_operation_valid <= 'd0;end
end
always @(posedge w_clk_125khz or posedge w_clk_125khz_rst)beginif(w_clk_125khz_rst)ri_user_write_date <= 'd0;else if(ri_user_write_valid)ri_user_write_date <= ri_user_write_date + 1;elseri_user_write_date <= ri_user_write_date;
end always @(posedge w_clk_125khz or posedge w_clk_125khz_rst)beginif(w_clk_125khz_rst)ri_user_write_sop <= 'd0;else if(w_user_active && ri_user_operation_type == P_W)ri_user_write_sop <= 'd1;elseri_user_write_sop <= 'd0;
end
always @(posedge w_clk_125khz or posedge w_clk_125khz_rst)beginif(w_clk_125khz_rst)ri_user_write_valid <= 'd0;else if(ri_user_write_eop)ri_user_write_valid <= 'd0;else if(w_user_active && ri_user_operation_type == P_W)ri_user_write_valid <= 'd1;elseri_user_write_valid <= ri_user_write_valid;
end
always @(posedge w_clk_125khz or posedge w_clk_125khz_rst)beginif(w_clk_125khz_rst)ri_user_write_eop <= 'd0;// else if((w_user_active || ri_user_write_valid) && r_write_cnt == P_WRITE_NUM - 2)// ri_user_write_eop <= 'd1;else if(w_user_active && P_WRITE_NUM == 1)ri_user_write_eop <= 'd1;//write 1 byteelse if(ri_user_write_valid && r_write_cnt == P_WRITE_NUM - 2)ri_user_write_eop <= 'd1;//write over 1 byteelseri_user_write_eop <= 'd0;
end
always @(posedge w_clk_125khz or posedge w_clk_125khz_rst)beginif(w_clk_125khz_rst)r_write_cnt <= 'd0;else if(r_write_cnt == P_WRITE_NUM - 1)r_write_cnt <= 'd0;else if(ri_user_write_valid)r_write_cnt <= r_write_cnt + 1'd1;elser_write_cnt <= r_write_cnt;
end
always @(posedge w_clk_125khz or posedge w_clk_125khz_rst)beginif(w_clk_125khz_rst)r_wr_st <= 'd0;else if(w_user_active)r_wr_st <= r_wr_st + 1'd1;elser_wr_st <= r_wr_st;
end
endmodule
相关文章:
FPGA通过I2C控制AT24C64
文章目录 前言一、代码设计框图二、IIC_drive模块设计2.1、模块接口:2.2、代码功能描述:2.3、IIC协议实现过程: 三、EEPROM_ctrl模块设计3.1、模块接口:3.2、代码功能描述 四、EEPROM_drive模块五、iic_top模块 前言 继上一篇FPG…...
134. 加油站(力扣LeetCode)
文章目录 134. 加油站题目描述暴力枚举(超时)代码一代码二(优化) 贪心算法方法一方法二 134. 加油站 题目描述 在一条环路上有 n 个加油站,其中第 i 个加油站有汽油 gas[i] 升。 你有一辆油箱容量无限的的汽车&…...
XSKY 智能存储,助力“数据要素 X”先进制造
3 月 21-22 日,主题为“突破 智行”的 IMC2024 第七届中国智造数字科技峰会在重庆召开。作为在先进制造领域拥有领先存储解决方案以及众多应用实践的企业,星辰天合受邀参加了此次峰会并荣获大会颁发的“最佳存储解决方案奖”。同时,星辰天合先…...
数据挖掘与分析学习笔记
一、Numpy NumPy(Numerical Python)是一种开源的Python库,专注于数值计算和处理多维数组。它是Python数据科学和机器学习生态系统的基础工具包之一,因为它高效地实现了向量化计算,并提供了对大型多维数组和矩阵的支持…...
linux docker镜像初始化
linux docker镜像初始化 简介 有的镜像内部使用的linux系统特别精简,许多常用命令无法安装,导致排查问题较为困难。 可以使用cat /etc/os-release查看容器使用的linux版本,再进行一些常用操作的初始化。 Debian # 设置镜像源 RUN rm -f /…...
专业140+总分410+南京大学851信号与系统考研经验南大电子信息与通信集成,电通,真题,大纲,参考书。
今年分数出来还是有点小激动,专业851信号与系统140(感谢Jenny老师辅导和全程悉心指导,答疑),总分410,梦想的南大离自己越来越近,马上即将复试,心中慌的一p,闲暇之余&…...
. ./ bash dash source 这五种执行shell脚本方式 区别
实际上,., ./, bash, dash, source 是五种不同的方式来执行 shell 脚本,它们之间有一些区别。 .(点号)或 source 命令:这两个命令是等价的,它们都是 Bash shell 内置的命令。它们用于在当前 shell 环境中执行脚本。当使用 . script.sh 或 source script.sh 命令来执行脚本…...
【React 】React 性能优化的手段有哪些?
1. 是什么 React凭借virtual DOM和diff算法拥有高效的性能,但是某些情况下,性能明显可以进一步提高 在前面文章中,我们了解到类组件通过调用setState方法,就会导致render ,父组件一旦发生render渲染,子组件一定也会执…...
3.22网络编程小项目
基于UDP的网络聊天室 项目需求: 如果有用户登录,其他用户可以收到这个人的登录信息如果有人发送信息,其他用户可以收到这个人的群聊信息如果有人下线,其他用户可以收到这个人的下线信息服务器可以发送系统信息 服务器 #includ…...
Git原理及使用
1、Git初识 Git是一种版本控制器: 对于同一份文件,做多次改动,Git会记录每一次改动前后的文件。 通俗的讲就是⼀个可以记录⼯程的每⼀次改动和版本迭代的⼀个管理系统,同时也⽅便多⼈协同作业。 注意: Git其实只能跟踪⽂本⽂件的改动,⽐如TXT⽂件,⽹⻚,所有的程序代码…...
Milvus 向量数据库介绍及使用
一、Milvus 介绍及安装 Milvus 于 2019 年创建,其目标只有一个:存储、索引和管理由深度神经网络和其他机器学习 (ML) 模型生成的大量嵌入向量。它具备高可用、高性能、易拓展的特点,用于海量向量数据的实时召回。 作为专门为处理输入向量查…...
STP环路避免实验(华为)
思科设备参考:STP环路避免实验(思科) 一,技术简介 Spanning Tree Protocol(STP),即生成树协议,是一种数据链路层协议。主要作用是防止二层环路,并自适应网络变化和故障…...
二、SpringBoot3 配置文件
本章概要 统一配置管理概述属性配置文件使用YAML 配置文件使用批量配置文件注入多环境配置和使用 2.1 统一配置管理概述 SpringBoot工程下,进行统一的配置管理,你想设置的任何参数(端口号、项目根路径、数据库连接信息等等)都集中到一个固定…...
二、阅读器的开发(初始)-- 2、阅读器开发
1、epubjs核心工作原理 1.1 epubjs的核心工作原理解析 epub电子书,会通过epubjs去实例化一个Book对象,Book对象会对电子书进行解析。Book对象可以通过renderTo方法去生成一个Rendition对象,Rendition主要负责电子书的渲染,通过R…...
【QT入门】 Qt自定义信号后跨线程发送信号
往期回顾: 【QT入门】 lambda表达式(函数)详解-CSDN博客 【QT入门】 Qt槽函数五种常用写法介绍-CSDN博客 【QT入门】 Qt实现自定义信号-CSDN博客 【QT入门】 Qt自定义信号后跨线程发送信号 由于Qt的子线程是无法直接修改ui,需要发送信号到ui线程进行修改…...
51单片机学习笔记7 串转并操作方法
51单片机学习笔记7 串转并操作方法 一、串转并操作简介二、74HC595介绍1. **功能**:2. **引脚**:3. **工作原理**:4. 开发板原理图(1)8*8 LED点阵:(2)74HC595 串转并: 三…...
微服务cloud--抱团取暖吗 netflix很多停更了
抱团只会卷,卷卷也挺好的 DDD 高内聚 低耦合 服务间不要有业务交叉 通过接口调用 分解技术实现的复杂性,围绕业务概念构建领域模型;边界划分 业务中台: 数据中台: 技术中台: 核心组件 eureka&#x…...
牛客笔试|美团2024春招第一场【测试方向】
第一题:小美的数组询问 小美拿到了一个由正整数组成的数组,但其中有一些元素是未知的(用 0 来表示)。 现在小美想知道,如果那些未知的元素在区间 [l, r] 范围内随机取值的话,数组所有元素之和的最小值和最大…...
Docker搭建LNMP环境实战(一):前言
缘起:不久前学习了Docker相关知识,并在Docker环境下学习了LNMP环境的搭建。由于网上的文章大多没有翔实、可行的案例,很多文章都是断章取义,所以,期间踩了太多太多的坑,初学者想要真正顺利地搭建一套环境起…...
SCI一区 | Matlab实现PSO-TCN-BiGRU-Attention粒子群算法优化时间卷积双向门控循环单元融合注意力机制多变量时间序列预测
SCI一区 | Matlab实现PSO-TCN-BiGRU-Attention粒子群算法优化时间卷积双向门控循环单元融合注意力机制多变量时间序列预测 目录 SCI一区 | Matlab实现PSO-TCN-BiGRU-Attention粒子群算法优化时间卷积双向门控循环单元融合注意力机制多变量时间序列预测预测效果基本介绍模型描述…...
浏览器访问 AWS ECS 上部署的 Docker 容器(监听 80 端口)
✅ 一、ECS 服务配置 Dockerfile 确保监听 80 端口 EXPOSE 80 CMD ["nginx", "-g", "daemon off;"]或 EXPOSE 80 CMD ["python3", "-m", "http.server", "80"]任务定义(Task Definition&…...
关于iview组件中使用 table , 绑定序号分页后序号从1开始的解决方案
问题描述:iview使用table 中type: "index",分页之后 ,索引还是从1开始,试过绑定后台返回数据的id, 这种方法可行,就是后台返回数据的每个页面id都不完全是按照从1开始的升序,因此百度了下,找到了…...
【第二十一章 SDIO接口(SDIO)】
第二十一章 SDIO接口 目录 第二十一章 SDIO接口(SDIO) 1 SDIO 主要功能 2 SDIO 总线拓扑 3 SDIO 功能描述 3.1 SDIO 适配器 3.2 SDIOAHB 接口 4 卡功能描述 4.1 卡识别模式 4.2 卡复位 4.3 操作电压范围确认 4.4 卡识别过程 4.5 写数据块 4.6 读数据块 4.7 数据流…...
【2025年】解决Burpsuite抓不到https包的问题
环境:windows11 burpsuite:2025.5 在抓取https网站时,burpsuite抓取不到https数据包,只显示: 解决该问题只需如下三个步骤: 1、浏览器中访问 http://burp 2、下载 CA certificate 证书 3、在设置--隐私与安全--…...
selenium学习实战【Python爬虫】
selenium学习实战【Python爬虫】 文章目录 selenium学习实战【Python爬虫】一、声明二、学习目标三、安装依赖3.1 安装selenium库3.2 安装浏览器驱动3.2.1 查看Edge版本3.2.2 驱动安装 四、代码讲解4.1 配置浏览器4.2 加载更多4.3 寻找内容4.4 完整代码 五、报告文件爬取5.1 提…...
html-<abbr> 缩写或首字母缩略词
定义与作用 <abbr> 标签用于表示缩写或首字母缩略词,它可以帮助用户更好地理解缩写的含义,尤其是对于那些不熟悉该缩写的用户。 title 属性的内容提供了缩写的详细说明。当用户将鼠标悬停在缩写上时,会显示一个提示框。 示例&#x…...
论文笔记——相干体技术在裂缝预测中的应用研究
目录 相关地震知识补充地震数据的认识地震几何属性 相干体算法定义基本原理第一代相干体技术:基于互相关的相干体技术(Correlation)第二代相干体技术:基于相似的相干体技术(Semblance)基于多道相似的相干体…...
C++:多态机制详解
目录 一. 多态的概念 1.静态多态(编译时多态) 二.动态多态的定义及实现 1.多态的构成条件 2.虚函数 3.虚函数的重写/覆盖 4.虚函数重写的一些其他问题 1).协变 2).析构函数的重写 5.override 和 final关键字 1&#…...
C++.OpenGL (20/64)混合(Blending)
混合(Blending) 透明效果核心原理 #mermaid-svg-SWG0UzVfJms7Sm3e {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}#mermaid-svg-SWG0UzVfJms7Sm3e .error-icon{fill:#552222;}#mermaid-svg-SWG0UzVfJms7Sm3e .error-text{fill…...
Python 实现 Web 静态服务器(HTTP 协议)
目录 一、在本地启动 HTTP 服务器1. Windows 下安装 node.js1)下载安装包2)配置环境变量3)安装镜像4)node.js 的常用命令 2. 安装 http-server 服务3. 使用 http-server 开启服务1)使用 http-server2)详解 …...
