Verilog 实现双边沿触发器Dual Edge_triggered_flip Flop

Verilog 实现双边沿触发器Dual Edge_triggered_flip Flop 在做HDLbits时,有一道很有趣的双边沿触发器问题 ,这里记录一下相关内容和解答方式。 问题描述 实现一个双边沿触发器,即在时钟的上升沿和下降沿都被触发。 module top_module ( input clk, input d, output q ); 问题 无法直接通过always @(posedge clk or negedge clk)直接创建双边沿触发器,FPGA 中只能存在单边沿触发器。 但是你可以创建两个触发器,分别是上升沿和下降沿。 解决方案(1) 虽然我们无法直接创建双边沿触发器,但是可以通过使用两个触发器和一个多路选择器实现相同的功能。 module top_module ( input clk, input d, output q ); reg q1; reg q2; always @(posedge clk) begin q1 <= d; end always @(negedge clk) begin q2 <= d; end assign q = clk ? q1 : q2; endmodule 注意,你可能想要两个触发器内都填写q <= d,这在思维上是合理的,但是在实现中会引入多驱问题。...

November 11, 2022 · yunlang

右值引用: 移动语义

右值引用:移动语义 左值与右值 左值有标识 标识:你有某个值,并有某个值的内存地址,可以安全的使用它 左值(lvalue)可以出现在赋值的左侧(当我们使用他的名称时),也可以出现在赋值的右侧(当我们使用他的值时)。因此当我们称某个值为左值时,他未必出现在等号左侧,而是认为他有标识。 这里的左值严格意义上称为泛左值,包括左值和将亡值两种。 右值可移动,左值不能 有些值并非泛左值,换句话说你无法获得其内存地址并使用。这类值的优点是可以移动他而不是复制它。(通常情况下移动要比赋值开销小很多)。移动一个值意味着他不会在原来的位置,当你称一个值可以移动时,我们认为是右值。 左值是不可移动的,因为这破坏了左值的概念:通过内存地址使用 右值引用的对象,是临时的,即将被销毁。 纯右值 纯右值没有标识,因此我们无法使用他的内存地址,但他是可以移动的(因为是右值)。 值类别汇总 泛左值(glvalue):有标识 左值:有标识但不能移动 将亡值:有标识,但也可以移动,是之前的某个左值变成了右值引用。 纯右值:没有标识,可以移动。 右值:可移动 左值持久,右值短暂 左值引用与右值引用 重新观察T& 重新观察T&和const T&,他们现在实际上是对左值的引用。左值引用可以绑定到左值,但不可以绑定到右值。 左值引用时,我们将一个对象的内存空间绑定到另一个变量上,因此我们使用的是一个对象在内存中的位置,这是一个左值。 右值引用 通过T&&可以标识一个类型T的右值引用,右值引用引用了一个可移动值,其内容在使用后无需保留。右值引用绑定到右值而非左值(右值引用假定内容无需保留而进行移动的值)。 右值引用意味着:1.右值是临时的,即将被销毁。 2.右值引用的对象不会在其他地方使用。 这两个特性意味着:接受和使用右值引用的代码,可以自由地接管所引用的对象的资源,而无需担心对其他代码逻辑造成数据破坏。 右值引用是左值还是右值 对于左值引用,当我们想要使用他的值时,他是右值,当我们想要使用他的地址(内存空间)时,他是左值。对于右值引用也一样,当我们进行右值引用时,右值的变量已经被右值引用接管了,这个时候的变量可以通过右值引用保存下来,因此可以成为左值。而我们也可以直接使用右值引用的值,这个时候右值引用会作为右值。 移动语义 右值引用支持“移动语义”,利用移动语义,你可以让一个对象转移到另一个对象而非使用拷贝构造,他也可以使用临时对象转移资源。 右值中的数据可以被安全移走使得右值可以用来表达移动语义。 考虑vector对象的实例,当vector容量满时,我们会开辟一块新的空间并将内容拷贝构造到新空间,销毁之前的空间。但拥有了移动语义后,我们可以实现移动而非拷贝,这可以避免成本高昂的内存分配和复制操作。

October 7, 2022 · yunlang

数据库系统(一)

数据库系统 数据库 什么是数据库? 将信息以某种形式存储在一起。 数据库的重要位置 系统软件之一,为多种应用软件提供基础。 注意数据库(Database)与数据库管理系统(Database management system,DBMS)的区别。 传统数据整理 传统数据整理的方式:一种方式为 CSV 的表格式存储。 缺点:安全性,效率性,使用时的复杂度等。 如无法保证在数字栏插入的一定是数字。检索需要遍历,出现问题容易直接崩溃等。 早期的DBMS DBMS:软件层面上对数据模型进行定义,提供了增删改查等功能。 早期的数据模型:逻辑与物理紧密结合,必须对特定的数据库场景安排对应的处理应用。 根本原因为物理存储上直接采用应用对数据格式,位置等进行规定,因此切换场景等都需要重新进行设计。 关系模型 基于关系定义了一种数据模型的抽象。 利用一种简单的数据结构(关系)进行数据库存储 用户操作基于高级语言,DBMS 负责具体执行策略 物理存储由 DBMS 负责实现。 关系模型是将无序的各种数据通过关系串联起来,而对这些数据的操作和物理存储的实现都交给了 DBMS,因此使用者可以相对透明的完成对数据的处理。 关系模型也定义了三个概念: 数据结构 数据操作 数据约束 关系模型利用了数学上的关系定义 主键与外键 主键:每个关系中唯一的键,作为该关系的关键字。(如省略,一般会自动生成) 外键:提供关系与关系间的纽带。 DML Data Manipulation Languages,数据操作语言,用来操作数据库表中的记录。 中文可以理解成增删改查四种操作。 常见的两种分类: Procedural: 指定了做什么,和如何做 Non-Procedural(Declaratice): 仅仅指定了做什么 关系代数 关系代数是对关系模型中各种运算操作的集合(前面说了关系模型其实是一种数学的关系定义)。 注意和数学上的关系运算并不完全相同。 “选择”、“投影”、笛卡尔积(也叫做“叉积”或“交叉连接”)、并集、差集、“重命名”、“自然连接”。 利用关系代数我们可以解释两种 DML 的不同之处: Procedural:σb id=102(R ▷◁ S),既解释了做什么,也解释了如何做 Non-Procedural:(retrieve the joined tuples from R and S where bid equals 102,只说明了做什么,没有说明如何做,指定关系代数顺序) 第二种交给了 DBMS 来完成。...

September 2, 2022 · yunlang

利用分支完成 github pages 博客内容存放和页面部署

前言 我利用github pages作为平台搭建我的博客,我开始选择将博客内容和部署分成两个仓库存放,但这显然造成了复杂性的提升。在阅读 mdbook 的官方文档时,我发现他部署 book 的一个方式是利用一个新的分支进行部署,这样可以将内容和页面放在不同的分支上共同保存,同时有好的规整感。 原理 在 github 仓库的 Settings/Pages 下可以选择利用哪一个分支进行部署。 利用 github worktree 可以将当前分支绑定到一个新建的 worktree 目录上,并通过新的目录进行分支操作。 使用 新建分支 deploy 和 /tmp/blog 目录,利用github worktree 将目录 deploy 分支绑定到目录下。 将生成的页面文件(我这里在public文件夹中),拷贝到 /tmp/blog 目录下 在 /tmp/blog 下利用 git 操作,添加并提交到远程 deploy 分支中。 设置 github pages,用 deploy 分支作为 github pages 部署分支。 现在你可以将内容提交到 main 分支,而将部署提交到 deploy分支。 为什么使用临时目录 使用临时目录的样例来自 mdbook 的文档。因此我只是当一个黑盒来使用。我的想法是为了不破坏其他数据,不过有了解的朋友也欢迎来给我答疑解惑。 我的 Makefile 文件 .PHONY: deploy .PHONY: clean .PHONY: build .PHONY: commit clean: rm -rf public deploy: public @echo "====> deploying to github" -mkdir /tmp/blog git worktree prune -git worktree add /tmp/blog deploy rm -rf /tmp/blog/* cp -rp public/* /tmp/blog/ cd /tmp/blog && \ git add -A && \ git commit -m "deployed on $(shell date) by ${USER}" && \ git push origin deploy cd - build: hugo commit: git add Makefile config....

September 2, 2022 · yunlang

数据处理练习

目标 对这个 网页中的数据集进行数据处理,选择一列 找出最大值和最小值, 选择其中两列求出差值并求和. 步骤 对于html, 可以使用wget或curl读入. 处理html内容可以采用pup工具来实现. 下载网页到本地 wget https://stats.wikimedia.org/EN/TablesWikipediaZZ.htm -O pra.html 对网站元素进行查看 最好的方法是使用浏览器的审查元素方式进行查看, 能够较快的找到自己所需的内容. 可以看到我们所需的数据表格在table中,id为table1.更近一步观察可以看到位于tbody中.可以通过pup过滤并 输出内容. 数据处理 通过pup获取html中第一个表格的数据 cat pra.html | pup 'table#table1 tbody td next{}' 此时内容如图 去除头部和尾部部分行 对于表格文件,我只关心表格中间的数据,而忽略表头和表尾,这里采用head和tail进行过滤. 删除尾部30行,删除头部208(209-1)行. head -n -30 tail -n +209 将列变为行,以空格分割 相对于一列,我更喜欢处理以整行数据,这样就可以利用awk的$获取分割. 通过tr命令进行替换 tr '\n' ' ' awk awk是一种善于处理文本的编程语言,他太强大了,以至于我们可以用awk完成其余的所有操作. awk '{sum = 0;max = 0; min = 65536;for(i = 2;i < 4302; i+=20) {if(max < $i) max = $i; if(min > $i) \ min = $i; if($i > $(i+1)) sum += $i - $(i+1); if($i <= $(i+1)) sum += $(i+1) - $i;}print max; print \ min; print sum } 正如我们所说,awk是一种编程语言,代码块中,$0 表示整行的内容,$1 到 $n 为一行中的 n 个区域,区域的 分割基于 awk 的域分隔符(默认是空格,可以通过-F来修改)。...

May 14, 2022 · yunlang