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

Verilog基础(三):过程

过程(Procedures)

- Always块 – 组合逻辑 (Always blocks – Combinational)

由于数字电路是由电线相连的逻辑门组成的,所以任何电路都可以表示为模块和赋值语句的某种组合.

然而,有时这不是描述电路最方便的方法.

两种always block是十分有用的:

  • 组合逻辑: always @(*)
  • 时序逻辑: always @(posedge clk)

always @(*)就相当于赋值语句–assign,因此选择哪一种语法仅仅取决与方便程度.

block内还有更丰富的语句集,比如if-else,case等等.但不能包含连续赋值即不可包含assign,因为他与always @(*)冲突.

以下语句是等价的

assign out1 = a & b | c ^ d;
always @(*) out2 = a & b | c ^ d;

  • Module Declaraction
module top_module(input a, input b,output wire out_assign,output reg out_alwaysblock
);
  • Solution
// synthesis verilog_input_version verilog_2001
module top_module(input a, input b,output wire out_assign,output reg out_alwaysblock
);assign out_assign = a&b;always @(*) out_alwaysblock = a&b;
endmodule
- Always块 – 时序逻辑 (Always blocks – Clocked)

verilog中有三种赋值方式:

  • 连续赋值: assign x = y; 不能在always-block内使用
  • 阻塞赋值: x = y;, 只能在always-block内使用
  • 非阻塞赋值: x <= y,只能在always-block内使用

请在组合逻辑中使用阻塞赋值,在时序逻辑中使用非阻塞赋值
否则将产生难以发现的错误

请实现如下电路:

  • Module Declaraction
module top_module(input clk,input a,input b,output wire out_assign,output reg out_always_comb,output reg out_always_ff   );
  • Solution
// synthesis verilog_input_version verilog_2001
module top_module(input clk,input a,input b,output wire out_assign,output reg out_always_comb,output reg out_always_ff   );
assign out_assign = a^b;always @(*) out_always_comb = a^b;always @(posedge clk) out_always_ff <= a^b;
endmodule
- If语句

if语句通常创建一个2对1的多路选择器,如果条件为真,则选择一个输入,如果条件为假,则选择另一个输入.

以下两种写法是等价的:

always @(*) beginif (condition) beginout = x;endelse beginout = y;end
endassign out = (condition) ? x : y;

建立一个在a和b之间选择的2对1多路选择器.如果sel_b1和sel_b2都为真,则选择b.否则,选择a.

执行相同的操作两次,一次使用assign语句,一次使用if语句.

  • Module Declaraction
module top_module(input a,input b,input sel_b1,input sel_b2,output wire out_assign,output reg out_always   ); 
  • Solution
// synthesis verilog_input_version verilog_2001
module top_module(input a,input b,input sel_b1,input sel_b2,output wire out_assign,output reg out_always   ); assign out_assign = (sel_b1&sel_b2)?b:a;always @(*) beginif(sel_b1&sel_b2) beginout_always = b;endelse beginout_always = a;endend
endmodule
- If语句引发的锁存(latches)

以下代码包含锁存的错误行为.

  • Module Declaraction
always @(*) beginif (cpu_overheated)shut_off_computer = 1;
endalways @(*) beginif (~arrived)keep_driving = ~gas_tank_empty;
end
  • Solution
// synthesis verilog_input_version verilog_2001
module top_module (input      cpu_overheated,output reg shut_off_computer,input      arrived,input      gas_tank_empty,output reg keep_driving  ); //always @(*) beginif (cpu_overheated) beginshut_off_computer = 1;endelse beginshut_off_computer = 0;endendalways @(*) beginif (~arrived&~gas_tank_empty) beginkeep_driving = ~gas_tank_empty&(~arrived);endelse beginkeep_driving = ~(gas_tank_empty|arrived);endendendmodule

If语句在硬件描述语言(如Verilog)中用于描述受条件控制的电路。然而,不当的If语句使用可能会引发锁存器(latches)的产生,这在FPGA或ASIC设计中通常是不希望看到的。以下是对If语句引发锁存器的详细分析:

  • 一、锁存器的基本概念

锁存器是一种在异步电路系统中对输入信号电平敏感的单元,用来存储信息。当锁存信号有效时,数据被锁存,输入信号不再起作用。锁存器也被称为透明锁存器,因为不锁存时输出对于输入是透明的。

  • 二、If语句引发锁存器的情况

    在Verilog中,If语句引发锁存器的情况主要包括以下几种:

    1. 组合逻辑中If语句缺少Else分支

      • 在组合逻辑电路中,如果If语句没有覆盖所有可能的条件,并且没有提供Else分支来指定其他条件下的输出,那么综合工具可能会推断出一个锁存器行为来保持上一个状态。
      • 例如,if (enable) reg <= data;enable为假时,reg的值将保持不变,这可能导致锁存器的产生。
    2. 敏感信号列表不完整

      • always块中使用非阻塞赋值(<=)时,如果没有显式的敏感信号列表或者敏感信号列表不完整,也可能导致锁存器的产生。
      • 这是因为综合器可能无法正确判断何时应更新信号,从而推断出锁存器行为来保持信号状态。
    3. 输出变量赋值给自己

      • 在If语句或组合逻辑中,如果输出变量被赋值给自己(即赋值表达式中包含输出变量自身),也可能导致锁存器的产生。
      • 这是因为输出变量需要具有存储功能来保持其上一个状态。
  • 三、避免If语句引发锁存器的策略

    为了避免If语句引发锁存器,可以采取以下策略:

    1. 确保If语句结构完整

      • 在组合逻辑中,确保If语句覆盖所有可能的条件,并提供Else分支来指定其他条件下的输出。
      • 这有助于确保输出在所有条件下都有一个已知的状态,从而避免锁存器的产生。
    2. 使用阻塞赋值明确表达组合逻辑

      • 在组合逻辑中,使用阻塞赋值(=)来明确表达逻辑关系,而不是使用非阻塞赋值。
      • 这有助于综合工具正确识别组合逻辑并避免推断出锁存器。
    3. 完善敏感信号列表

      • 在使用非阻塞赋值时,确保always块有完整的敏感信号列表。
      • 这有助于综合工具正确判断何时应更新信号并避免锁存器的产生。
    4. 避免输出变量赋值给自己

      • 在组合逻辑中,避免将输出变量赋值给自己。
      • 如果需要保持上一个状态,可以考虑使用触发器(Flip-Flop)而不是锁存器。
  • 四、锁存器的危害与替代方案

锁存器在FPGA或ASIC设计中可能带来以下危害:

  1. 不可预测的时序行为:锁存器的输出取决于输入信号的持续电平,而不是特定的时钟边沿,这使得时序分析和预测更加困难。
  2. 系统不稳定:由于锁存器的输出直接由输入决定,任何输入上的噪声或毛刺都会立即反映到输出上,可能导致系统不稳定或误操作。
  3. 资源利用率降低:FPGA内部的锁存器实现通常不如寄存器高效,可能降低资源利用率并增加功耗。

因此,在FPGA设计中,通常推荐使用寄存器(触发器)来代替锁存器,除非有特殊的应用场景要求锁存器的使用。寄存器在时钟边沿更新,提供了更可预测和稳定的行为,便于时序分析和设计验证。

综上所述,If语句在硬件描述语言中的使用需要谨慎,以避免引发不必要的锁存器。通过确保If语句结构完整、使用阻塞赋值明确表达组合逻辑、完善敏感信号列表以及避免输出变量赋值给自己等策略,可以有效避免锁存器的产生。


- Case语句

verilog中的case语句几乎等同于if elseif else的序列,该序列将一个表达式与其他表达式列表进行比较.它的语法和功能与C语言中的switch语句不同.

always @(*) begin     // This is a combinational circuitcase (in)1'b1: begin out = 1'b1;  // begin-end if >1 statementend1'b0: out = 1'b0;default: out = 1'bx;endcase
end
  • case语句以case开头,每个"case item"以冒号结尾,没有switch
  • 每个case项只能执行一条语句.这使得C中使用的“break”不必要.但这意味着如果需要多个语句,必须使用begin…end

如果有大量选项的情况,case语句比if语句更方便.因此,在本练习中,创建一个6对1的多路选择器.当sel介于0和5之间时,选择相应的数据输入,否则,输出0.数据输入和输出均为4位宽.小心锁存.

  • Module Declaraction
module top_module ( input [2:0] sel, input [3:0] data0,input [3:0] data1,input [3:0] data2,input [3:0] data3,input [3:0] data4,input [3:0] data5,output reg [3:0] out   );
  • Solution
// synthesis verilog_input_version verilog_2001
module top_module ( input [2:0] sel, input [3:0] data0,input [3:0] data1,input [3:0] data2,input [3:0] data3,input [3:0] data4,input [3:0] data5,output reg [3:0] out   );//always@(*) begin  // This is a combinational circuitcase(sel)3'b0: beginout = data0;end3'b001: beginout = data1;end3'b010: beginout = data2;end3'b011: beginout = data3;end3'b100: beginout = data4;end3'b101: beginout = data5;enddefault: beginout[3:0] = 0;endendcaseendendmodule
- 简单编码器1

priority encoder是一种组合电路,当输入一个vector时,输出第一个’1’出现的位置.例如:输入8’b10010000,输出3’d4,因为[4]是第一个高位.
构建一个4位encoder,若全是低位则输出0.

  • Module Declaraction
module top_module (input [3:0] in,output reg [1:0] pos  );
  • Solution
// synthesis verilog_input_version verilog_2001
module top_module (input [3:0] in,output reg [1:0] pos  );always @(*) beginif (in[0] == 1'b1) beginpos = 2'd0;endelse beginif(in[1] == 1'b1) beginpos = 2'd1;endelse beginif(in[2] == 1'b1) beginpos = 2'd2;endelse beginif(in[3] == 1'b1) beginpos = 2'd3;endelse beginpos = 0;endendendendend
endmodule
- 简单编码器2

假如现在输入是8位,那么就会有256种情况,我们可以使用casez来将item减少到9种.
例如:

always @(*) begincasez (in[3:0])4'bzzz1: out = 0;   // in[3:1] can be anything4'bzz1z: out = 1;4'bz1zz: out = 2;4'b1zzz: out = 3;default: out = 0;endcase
end
  • Module Declaraction
module top_module (input [7:0] in,output reg [2:0] pos  );
  • Solution
// synthesis verilog_input_version verilog_2001
module top_module (input [7:0] in,output reg [2:0] pos  );
always @(*) begincasez (in[7:0])8'bzzzzzzz1: beginpos = 3'd0;end8'bzzzzzz1z: beginpos = 3'd1;end8'bzzzzz1zz: beginpos = 3'd2;end8'bzzzz1zzz: beginpos = 3'd3;end8'bzzz1zzzz: beginpos = 3'd4;end8'bzz1zzzzz: beginpos = 3'd5;end8'bz1zzzzzz: beginpos = 3'd6;end8'b1zzzzzzz: beginpos = 3'd7;enddefault: beginpos = 0;endendcase
end
endmodule
- 避免锁存

假设您正在构建一个电路来处理游戏中PS/2键盘的扫描代码.

接收到的最后两个字节的扫描代码,您需要判断是否已按下键盘上的一个箭头键.这涉及到一个相当简单的映射,它可以使用一个case语句(或者如果elseif)实现,有四个case.

Scancode [15:0]Arrow key
16’he06bleft arrow
16’he072down arrow
16’he074right arrow
16’he075up arrow
Anythingelse none

为了避免创建锁存,必须在所有可能的条件下为所有输出分配一个值

  • Module Declaraction
module top_module (input [15:0] scancode,output reg left,output reg down,output reg right,output reg up  ); 
  • Solution
// synthesis verilog_input_version verilog_2001
module top_module (input [15:0] scancode,output reg left,output reg down,output reg right,output reg up  ); always @(*) beginleft = 0;down = 0;left = 0;right = 0;case (scancode)16'he06b: beginleft = 1;end16'he072: begindown = 1;end16'he074: beginright = 1;end16'he075: beginup = 1;enddefault: beginup = 0;down = 0;left = 0;right = 0;endendcaseend
endmodule

更多语法特点

verilog也有像C一样的三目算符:

- 三目算符

verilog也有像C一样的三目算符:

condition ? true : false;

给定四个无符号数,求其最小值.

  • Module Declaraction
module top_module (input [7:0] a, b, c, d,output [7:0] min);
  • Solution
module top_module (input [7:0] a, b, c, d,output [7:0] min);//// assign intermediate_result1 = compare? true: false;wire [7:0]min1,min2;assign min1=(a<b?a:b);assign min2 = (min1<c?min1:c);assign min = (min2<d?min2:d);
endmodule
- 优化运算1

奇偶校验经常被用来作为一种简单的方法检测错误.

创建一个电路,该电路将为一个8位字节计算一个奇偶校验位.

即计算输入8个位的异或

  • Module Declaraction
module top_module (input [7:0] in,output parity); 
  • Solution
module top_module (input [7:0] in,output parity); assign parity = ^in[7:0];
endmodule
- 优化运算2

建立如下电路:

  • out_and: 对输入数据求与

  • out_or: 对输入数据求或

  • out_xor:对输入数据求异或

  • Module Declaraction

module top_module( input [99:0] in,output out_and,output out_or,output out_xor 
);
  • Solution
module top_module( input [99:0] in,output out_and,output out_or,output out_xor 
);assign out_and = &in[99:0];assign out_or = |in[99:0];assign out_xor = ^in[99:0];
endmodule
- 循环 – 组合逻辑:实现Vector反转

反转vector顺序

  • Module Declaraction
module top_module( input [99:0] in,output [99:0] out
);
  • Solution
module top_module( input [99:0] in,output [99:0] out
);integer i;always @(*) beginfor(i=0;i<=99;i=i+1)out[7'd99-i] <= in[i];end
endmodule
- 循环 – 组合逻辑:实现255位计数器

计算vector中1的个数

  • Module Declaraction
module top_module( input [254:0] in,output [7:0] out );
  • Solution
module top_module( input [254:0] in,output [7:0] out );integer i;reg [7:0]count;always @(*) begincount=0;for(i=0;i<=254;i=i+1) beginif(in[i] == 1) begincount = count + 7'b1;endendendassign out = count;
endmodule
- 循环:实现100位加法器

通过实例化100个全加器构建一个100位加法器.

  • Module Declaraction
module top_module( input [99:0] a, b,input cin,output [99:0] cout,output [99:0] sum );
  • Solution
module top_module( input [99:0] a, b,input cin,output [99:0] cout,output [99:0] sum );reg [100:0]cin1;generategenvar i;for(i=0;i<100;i=i+1) begin:addsif(i==0) begin        add ins(a[i],b[i],cin,sum[i],cout[i]);            assign cin1[i+1]=cout[i];end            else beginadd ins(a[i],b[i],cin1[i],sum[i],cout[i]);assign cin1[i+1]=cout[i];            endendendgenerate
endmodulemodule add(input a, input b, input cin, output sum, output cout);assign {cout,sum}=a+b+cin;
endmodule
- 循环:实现100位BCD加法器

在Verilog中实现一个100位的BCD(Binary-Coded Decimal)加法器相对复杂,因为BCD编码的每个数字占用4位二进制数,所以100位的BCD数实际上表示的是25位的十进制数(100位 / 4位/十进制数字 = 25个十进制数字)。

BCD加法的一个关键问题是进位处理。在普通的二进制加法中,进位是逐位传递的,但在BCD加法中,每四位(一个BCD数字)之间可能需要额外的调整来处理从低位到高位的进位,以确保结果仍然是有效的BCD数。这通常涉及到将非BCD的中间结果转换为BCD格式。

以下是一个简化的Verilog代码示例,用于实现两个4位BCD数的加法,并调整结果以确保它是有效的BCD数。请注意,这个示例并没有直接扩展到100位,但它提供了一个基础,你可以在这个基础上构建更复杂的100位BCD加法器。

module bcd_adder_4bit(input [3:0] a, // 4-bit BCD inputinput [3:0] b, // 4-bit BCD inputinput cin,     // Carry-inoutput [3:0] sum, // 4-bit BCD outputoutput cout    // Carry-out
);wire [4:0] temp_sum; // 5-bit temporary sum to handle carrywire [3:0] adjusted_sum; // 4-bit adjusted BCD sumwire temp_cout; // Temporary carry-out// Perform binary addition of the BCD digits and the carry-inassign temp_sum = a + b + cin;assign temp_cout = (temp_sum[4] == 1'b1); // Carry-out if the sum is 5-bits wide// BCD adjustment: if the result is greater than or equal to 10 (0xA in BCD), adjust it// to be in the range 0-9 by subtracting 6 (0x6 in BCD) and setting the carry-out for the next BCD digitassign adjusted_sum = (temp_sum >= 4'd10) ? (temp_sum - 4'd6) : temp_sum[3:0];// Carry-out for the next BCD digit is set if the original sum was 10 or more, or if there was a carry-in and the sum was exactly 9wire carry_adjustment = (temp_sum == 4'd10) | (cin && temp_sum == 4'd9);assign cout = temp_cout | carry_adjustment;// Output the adjusted sumassign sum = adjusted_sum;endmodule

要构建一个100位的BCD加法器,你需要将上述4位BCD加法器模块级联25次(因为100位/4位/数字=25个数字)。每个模块的输出cout将作为下一个模块的cin。同时,你需要一个额外的机制来处理最高位可能产生的进位(如果两个加数的和超过最大的25位BCD数)。

请注意,这个示例代码没有考虑所有可能的边界情况和优化。在实际应用中,你可能需要更复杂的逻辑来处理溢出、零检测、符号扩展等问题。此外,对于大规模设计,使用高级综合工具或手动优化可能有助于提高性能和资源利用率。

相关文章:

Verilog基础(三):过程

过程(Procedures) - Always块 – 组合逻辑 (Always blocks – Combinational) 由于数字电路是由电线相连的逻辑门组成的&#xff0c;所以任何电路都可以表示为模块和赋值语句的某种组合. 然而&#xff0c;有时这不是描述电路最方便的方法. 两种always block是十分有用的&am…...

生成式AI安全最佳实践 - 抵御OWASP Top 10攻击 (上)

今天小李哥将开启全新的技术分享系列&#xff0c;为大家介绍生成式AI的安全解决方案设计方法和最佳实践。近年来&#xff0c;生成式 AI 安全市场正迅速发展。据 IDC 预测&#xff0c;到 2025 年全球 AI 安全解决方案市场规模将突破 200 亿美元&#xff0c;年复合增长率超过 30%…...

.Net WebAPI -[HttpPut(“{fileServiceId:int}“)]

[HttpPut("{fileServiceId:int}")] 这个写法是 ASP.NET Core 中的一个路由特性&#xff0c;用于定义一个 HTTP PUT 请求的路由&#xff0c;并指定路由参数的类型。 解析 HttpPut [HttpPut]&#xff1a; 这是一个 ASP.NET Core 的路由特性&#xff0c;用于标记一个方…...

[EAI-027] RDT-1B,目前最大的用于机器人双臂操作的机器人基础模型

Paper Card 论文标题&#xff1a;RDT-1B: a Diffusion Foundation Model for Bimanual Manipulation 论文作者&#xff1a;Songming Liu, Lingxuan Wu, Bangguo Li, Hengkai Tan, Huayu Chen, Zhengyi Wang, Ke Xu, Hang Su, Jun Zhu 论文链接&#xff1a;https://arxiv.org/ab…...

C基础寒假练习(7)

一、有 1、2、3、4个数字&#xff0c;能组成多少互不相同且无重复的三位&#xff1f; 都是多少&#xff1f; #include <stdio.h> int main() {// 定义数字数组int digits[] {1, 2, 3, 4};int n sizeof(digits) / sizeof(digits[0]);// 嵌套循环遍历所有排列for (int …...

Ajax:重塑Web交互体验的人性化探索

在数字化时代&#xff0c;网页的交互性和响应速度已成为衡量用户体验的关键指标。Ajax&#xff08;Asynchronous JavaScript and XML&#xff09;&#xff0c;作为前端与后端沟通的桥梁&#xff0c;凭借其异步通信的能力&#xff0c;极大地提升了网页的动态性和用户友好度&…...

【DeepSeek背后的技术】系列二:大模型知识蒸馏(Knowledge Distillation)

目录 1 引言2 操作步骤和公式说明2.1 准备教师模型&#xff08;Teacher Model&#xff09;和学生模型&#xff08;Student Model&#xff09;2.2 生成软标签&#xff08;Soft Labels&#xff09;2.3 定义蒸馏损失函数2.4 训练学生模型2.5 调整超参数2.6 评估与部署 3 其他知识蒸…...

【Numpy核心编程攻略:Python数据处理、分析详解与科学计算】2.14 内存映射:处理超大型数组的终极方案

2.14 内存映射&#xff1a;处理超大型数组的终极方案 目录 #mermaid-svg-G91Kn9O4eN2k8xEo {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}#mermaid-svg-G91Kn9O4eN2k8xEo .error-icon{fill:#552222;}#mermaid-svg-G91Kn9O4eN2k…...

【C++】STL——vector的使用

目录 &#x1f495;1.vector介绍 &#x1f495;2.vector的基本用法 &#x1f495;3.vector功能的具体用法 &#xff08;讲解&#xff09; &#x1f495;4.vector——size&#xff0c;capacity函数的使用 &#xff08;简单略讲&#xff09; &#x1f495;5.resize&#xff…...

springboot/ssm互联网智慧医院体检平台web健康体检管理系统Java代码编写

springboot/ssm互联网智慧医院体检平台web健康体检管理系统Java代码编写 基于springboot(可改ssm)vue项目 开发语言&#xff1a;Java 框架&#xff1a;springboot/可改ssm vue JDK版本&#xff1a;JDK1.8&#xff08;或11&#xff09; 服务器&#xff1a;tomcat 数据库&am…...

介绍一下Mybatis的Executor执行器

Executor执行器是用来执行我们的具体的SQL操作的 有三种基本的Executor执行器&#xff1a; SimpleExecutor简单执行器 每执行一次update或select&#xff0c;就创建一个Statement对象&#xff0c;用完立刻关闭Statement对象 ReuseExecutor可重用执行器 可重复利用Statement…...

Wide Deep 模型:记忆能力与泛化能力

实验和完整代码 完整代码实现和jupyter运行&#xff1a;https://github.com/Myolive-Lin/RecSys--deep-learning-recommendation-system/tree/main 引言 Wide & Deep 模型是一种结合了线性模型&#xff08;Wide&#xff09;和深度神经网络&#xff08;Deep&#xff09;的混…...

Hot100之矩阵

73矩阵置零 题目 思路解析 收集0位置所在的行和列 然后该行全部初始化为0 该列全部初始化为0 代码 class Solution {public void setZeroes(int[][] matrix) {int m matrix.length;int n matrix[0].length;List<Integer> list1 new ArrayList<>();List<…...

Python语言的安全开发

Python语言的安全开发 引言 在信息技术迅速发展的今天&#xff0c;网络安全问题愈发凸显。随着Python语言的广泛应用&#xff0c;尤其是在数据分析、人工智能、Web开发等领域&#xff0c;其安全问题越来越受到重视。Python作为一门高效且易于学习的编程语言&#xff0c;虽然在…...

蓝桥杯刷题DAY3:Horner 法则 前缀和+差分数组 贪心

所谓刷题&#xff0c;最重要的就是细心 &#x1f4cc; 题目描述 在 X 进制 中&#xff0c;每一数位的进制不固定。例如&#xff1a; 最低位 采用 2 进制&#xff0c;第二位 采用 10 进制&#xff0c;第三位 采用 8 进制&#xff0c; 则 X 进制数 321 的十进制值为&#xff…...

java项目验证码登录

1.依赖 导入hutool工具包用于创建验证码 <dependency><groupId>cn.hutool</groupId><artifactId>hutool-all</artifactId><version>5.5.2</version></dependency> 2.测试 生成一个验证码图片&#xff08;生成的图片浏览器可…...

手写MVVM框架-环境搭建

项目使用 webpack 进行进行构建&#xff0c;初始化步骤如下: 1.创建npm项目执行npm init 一直下一步就行 2.安装webpack、webpack-cli、webpack-dev-server&#xff0c;html-webpack-plugin npm i -D webpack webpack-cli webpack-dev-server html-webpack-plugin 3.配置webpac…...

2025年2月2日(网络编程 tcp)

tcp 循环服务 import socketdef main():# 创建 socket# 绑定tcp_server socket.socket(socket.AF_INET, socket.SOCK_STREAM)tcp_server.bind(("", 8080))# socket 转变为被动tcp_server.listen(128)while True:# 产生专门为链接进来的客户端服务的 socketprint(&qu…...

【Docker项目实战】使用Docker部署MinIO对象存储(详细教程)

【Docker项目实战】使用Docker部署MinIO对象存储 前言一、 MinIO介绍1.1 MinIO简介1.2 主要特点1.3 主要使用场景二、本次实践规划2.1 本地环境规划2.2 本次实践介绍三、本地环境检查3.1 检查Docker服务状态3.2 检查Docker版本3.3 检查docker compose 版本四、下载MinIO镜像五、…...

使用ollama本地部署Deepseek r1

1、下载ollama 在浏览器地址输入&#xff1a;https://ollama.com/ 选择windows版本的下载 2、安装ollama 3、运行ollama 安装完成后&#xff0c;打开命令行工具win r 在命令行输入&#xff1a;ollama 4、使用ollama下载并部署Deepseed r1 在ollama网站&#xff0c;下载…...

19c补丁后oracle属主变化,导致不能识别磁盘组

补丁后服务器重启&#xff0c;数据库再次无法启动 ORA01017: invalid username/password; logon denied Oracle 19c 在打上 19.23 或以上补丁版本后&#xff0c;存在与用户组权限相关的问题。具体表现为&#xff0c;Oracle 实例的运行用户&#xff08;oracle&#xff09;和集…...

React 第五十五节 Router 中 useAsyncError的使用详解

前言 useAsyncError 是 React Router v6.4 引入的一个钩子&#xff0c;用于处理异步操作&#xff08;如数据加载&#xff09;中的错误。下面我将详细解释其用途并提供代码示例。 一、useAsyncError 用途 处理异步错误&#xff1a;捕获在 loader 或 action 中发生的异步错误替…...

MFC内存泄露

1、泄露代码示例 void X::SetApplicationBtn() {CMFCRibbonApplicationButton* pBtn GetApplicationButton();// 获取 Ribbon Bar 指针// 创建自定义按钮CCustomRibbonAppButton* pCustomButton new CCustomRibbonAppButton();pCustomButton->SetImage(IDB_BITMAP_Jdp26)…...

大型活动交通拥堵治理的视觉算法应用

大型活动下智慧交通的视觉分析应用 一、背景与挑战 大型活动&#xff08;如演唱会、马拉松赛事、高考中考等&#xff09;期间&#xff0c;城市交通面临瞬时人流车流激增、传统摄像头模糊、交通拥堵识别滞后等问题。以演唱会为例&#xff0c;暖城商圈曾因观众集中离场导致周边…...

【C语言练习】080. 使用C语言实现简单的数据库操作

080. 使用C语言实现简单的数据库操作 080. 使用C语言实现简单的数据库操作使用原生APIODBC接口第三方库ORM框架文件模拟1. 安装SQLite2. 示例代码:使用SQLite创建数据库、表和插入数据3. 编译和运行4. 示例运行输出:5. 注意事项6. 总结080. 使用C语言实现简单的数据库操作 在…...

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 提…...

MySQL用户和授权

开放MySQL白名单 可以通过iptables-save命令确认对应客户端ip是否可以访问MySQL服务&#xff1a; test: # iptables-save | grep 3306 -A mp_srv_whitelist -s 172.16.14.102/32 -p tcp -m tcp --dport 3306 -j ACCEPT -A mp_srv_whitelist -s 172.16.4.16/32 -p tcp -m tcp -…...

CMake控制VS2022项目文件分组

我们可以通过 CMake 控制源文件的组织结构,使它们在 VS 解决方案资源管理器中以“组”(Filter)的形式进行分类展示。 🎯 目标 通过 CMake 脚本将 .cpp、.h 等源文件分组显示在 Visual Studio 2022 的解决方案资源管理器中。 ✅ 支持的方法汇总(共4种) 方法描述是否推荐…...

Maven 概述、安装、配置、仓库、私服详解

目录 1、Maven 概述 1.1 Maven 的定义 1.2 Maven 解决的问题 1.3 Maven 的核心特性与优势 2、Maven 安装 2.1 下载 Maven 2.2 安装配置 Maven 2.3 测试安装 2.4 修改 Maven 本地仓库的默认路径 3、Maven 配置 3.1 配置本地仓库 3.2 配置 JDK 3.3 IDEA 配置本地 Ma…...

HarmonyOS运动开发:如何用mpchart绘制运动配速图表

##鸿蒙核心技术##运动开发##Sensor Service Kit&#xff08;传感器服务&#xff09;# 前言 在运动类应用中&#xff0c;运动数据的可视化是提升用户体验的重要环节。通过直观的图表展示运动过程中的关键数据&#xff0c;如配速、距离、卡路里消耗等&#xff0c;用户可以更清晰…...